# HG changeset patch # User cvs # Date 1186997171 -7200 # Node ID 11054d720c216703485b97cacbc88b6389bcb888 # Parent 28d9c139be4c2aab00e6088fac435441aac5781a Import from CVS: tag r21-2-20 diff -r 28d9c139be4c -r 11054d720c21 .cvsignore --- a/.cvsignore Mon Aug 13 11:25:03 2007 +0200 +++ b/.cvsignore Mon Aug 13 11:26:11 2007 +0200 @@ -7,3 +7,6 @@ GNUmakefile Makefile.in so_locations +xemacs-packages +mule-packages +site-packages diff -r 28d9c139be4c -r 11054d720c21 CHANGES-beta --- a/CHANGES-beta Mon Aug 13 11:25:03 2007 +0200 +++ b/CHANGES-beta Mon Aug 13 11:26:11 2007 +0200 @@ -1,4 +1,29 @@ -*- indented-text -*- +to 21.2.20 "Yoko" +-- UTF-8 & file-coding magic cookie fix from MORIOKA Tomohiko +-- bug fixes from Adrian Aichner, Sean MacLennan, and Jeff Miller +-- glyph widget support under X/Athena from Andy Piper +-- tab widget support under X (all variants) from Andy Piper +-- many gutter, redisplay & widget fixes from Andy Piper +-- mswindows mousewheel support from Mike Woolley +-- combo box support under X/Motif from Andy Piper +-- buffer tab grouping from Andy Piper +-- layout widget support from Andy Piper +-- partial display line scrolling support from Andy Piper +-- cleanup patches from Gleb Arshinov +-- hash table FSF API sync from Martin Buchholz +-- widget cleanup from Martin Buchholz +-- process-environment fix for nt from Julian Back +-- widget to frame fix from Jan Vroonhof +-- animated glyph support from Andy Piper +-- glyph redisplay improvements from Andy Piper +-- color cells allocation fix from Lee Kindness +-- recover file fix for windows nt +-- mingw install fix from Craig Lanning +-- recognize keypad keys under MS-Windows from Jonathan Harris +-- Switch gui dialogs to native widgets from Andy Piper +-- fixes from Yoshiki Hayashi and Norbert Koch + to 21.2.19 "Shinjuku" -- various fixes from Gunnar Evermann -- XIM fixes from Kazuyuki IENAGA diff -r 28d9c139be4c -r 11054d720c21 ChangeLog --- a/ChangeLog Mon Aug 13 11:25:03 2007 +0200 +++ b/ChangeLog Mon Aug 13 11:26:11 2007 +0200 @@ -1,3 +1,91 @@ +1999-11-10 XEmacs Build Bot + + * XEmacs 21.2.20 is released + +1999-09-21 Martin Buchholz + * configure.in: Autodetect Unix98 PTY + +1999-08-30 Robert Pluim + + * README.packages: Add description of package-get-provider + +1999-10-22 Vin Shelton + + * INSTALL: Added more information about README.packages, and + re-numbered some bullets. + +1999-10-24 Jan Vroonhof + + * INSTALL: Update disk requirements. Refer to README.packages + +1999-10-21 Andy Piper + + * configure.in (all_widgets): Only use xaw3d if we really have it. + +1999-10-06 Andy Piper + + * Makefile.in.in: use WINDOWSNT for mingw install. + +1999-08-01 Adrian Aichner + + * etc/DISTRIB: Update IP address of ftp.xemacs.org. + * etc/NEWS: Fix typo + +1999-09-25 Andy Piper + + * configure.in: check for Xaw3d and use in preference to Xaw + +1999-09-21 Martin Buchholz + + * Makefile.in.in: All Makefiles should #include config.h + +1999-09-19 Michael Sperber [Mr. Preprocessor] + + * configure.in (EMACS_CONFIGURATION): Use $configuration, not + $canonical, so that installation paths and dynamic path setup will + stay in synch. + +1999-09-20 Andy Piper + + * Makefile.in.in: use __CYGWIN32__ and __MINGW32__ to predicate + installation linkage. + +1999-08-29 Andreas Jaeger + + * configure.in (machine): Recognize MIPS/Linux. + +1999-08-27 Jan Vroonhof + + * modules/zlib/Makefile (distclean): + * modules/ldap/Makefile (distclean): + * modules/sample/Makefile (distclean): + * modules/base64/Makefile (distclean): new target + + * Makefile.in.in (top_distclean): Add package directories + (SUBDIR_DISTCLEAN): New variable, add module directories + +1999-09-01 Martin Buchholz + + * configure.in: Warn, but otherwise ignore, obsolete arguments. + +1999-08-20 Olivier Galibert + + * configure.in: Add --pdump option. + * configure.usage: Ditto. + +1999-08-04 Andy Piper + + * configure.in: report widget usage correctly. beef up setting. + + * Makefile.in.in: fix install-arch-dep for mingw32. + +1999-07-28 Andy Piper + + * config.h.in: add new LWLIB defines. + + * configure.in: fix definitions of widget defines with various + toolkit options. + 1999-07-30 XEmacs Build Bot * XEmacs 21.2.19 is released @@ -1872,7 +1960,7 @@ 1997-10-18 SL Baur - * XEmacs 20.3-beta91 is released. + * XEmacs 20.3-beta91 is released. 1997-10-16 Hrvoje Niksic @@ -3194,7 +3282,7 @@ Sat Mar 22 21:27:41 1997 Tomasz J. Cholewo - * configure.in: Echo only current configuration using 'tee -a'. + * configure.in: Echo only current configuration using 'tee -a'. Fri Mar 21 21:26:01 1997 Steven L Baur diff -r 28d9c139be4c -r 11054d720c21 INSTALL --- a/INSTALL Mon Aug 13 11:25:03 2007 +0200 +++ b/INSTALL Mon Aug 13 11:26:11 2007 +0200 @@ -1,6 +1,6 @@ XEmacs Installation Guide Copyright (c) 1994, 1995, 1996 Board of Trustees, University of Illinois -Copyright (c) 1994 Free Software Foundation, Inc. +Copyright (c) 1994-1999 Free Software Foundation, Inc. Synched up with: FSF 19.30. @@ -23,20 +23,22 @@ 1) Make sure your system has enough swapping space allocated to handle a program whose pure code is 900k bytes and whose data area is at - least 400k and can reach 8Mb or more. If the swapping space is + least 400k and can reach 8Mb or more. Note that a typical XEmacs + build is much bigger. If the swapping space is insufficient, you will get an error in the command `temacs -batch -l loadup dump', found in `./src/Makefile.in.in', or possibly when running the final dumped XEmacs. -Building XEmacs requires about 41 Mb of disk space (including the -XEmacs sources). Once installed, XEmacs occupies about 16 Mb in the -file system where it is installed; this includes the executable files, -Lisp libraries, miscellaneous data files, and on-line documentation. -The amount of storage of the Lisp directories may be reduced by -compressing the .el files. If the building and installation take place -in different directories, then the installation procedure temporarily -requires 41+16 Mb. Adjust this value upwards depending upon what -additional Lisp support is installed. + Verify that your users have a high enough stack limit. On some + systems such as OpenBSD and OSF/Tru64 the default is 2MB which is + too low. See 'PROBLEMS' for details. + +Building XEmacs requires about 100 Mb of disk space (including the +XEmacs sources). Once installed, XEmacs occupies between 20 and 100 Mb +in the file system where it is installed; this includes the executable files, +Lisp libraries, miscellaneous data files, and on-line documentation. The +exact amount depends greatly on the number of extra lisp packages that are +installed XEmacs requires an ANSI C compiler, such as GCC. If you wish to build the documentation yourself, you will need at least version 1.68 of @@ -65,20 +67,34 @@ XEmacs to allow configure to find the external software packages. If you link with dynamic (``.so'') external package libraries, which is not recommended, you will also need to add the library directories -to the --site-runtime-libraries option. - +to the --site-runtime-libraries option. For your convenience these can +be set together by using the --with-site-prefix command. This will set +these variables as needed assuming your libraries are organised as a +typical /usr tree. -3) Decide what Initial Lisp you need with XEmacs. XEmacs is -distributed separately from most of its runtime environment. This is +3) [N.B. Most of this section can be done during or after the +compilation of the core source code, but is present early to catch +your attention.] + +Decide what Initial Lisp you need with XEmacs. XEmacs is +distributed separately from most of its runtime environment. This is done to make it easier for administrators to tune an installation for -what the local users need. See the file etc/PACKAGES for an overview -of what is available and which packages need to be installed prior to -building XEmacs. At this point you only need a minimum to get started -at which point you may install what you wish without further changes -to the XEmacs binary. A sample minimum configuration for a Linux -system using Mule and Wnn6 from OMRON corporation would be the -packages `mule-base' and `egg-its'. By default, packages will be -searched for in the path +what the local users need. Note that while XEmacs will compile and +install without any packages present at least some additional lisp +packages are needed to bring XEmacs up to "normal" editor +functionality. Installation and upgrading of the packages can be done +almost automatically when from inside XEmacs when it has been compiled +and installed. + +More information and suggestions for which packages to install see the +file README.packages. + +IMPORTANT! The file README.packages contain information vital to have +a fully working XEmacs. This information was not included in this file +only because it is too large for this terse INSTALL. Please read +README.packages now! + +By default, packages will be searched for in the path ~/.xemacs::$prefix/lib/xemacs-${version}/mule-packages:$prefix/lib/xemacs/mule-packages:$prefix/lib/xemacs-${version}/xemacs-packages:$prefix/lib/xemacs/xemacs-packages @@ -380,7 +396,7 @@ same configuration. If `configure' exits with an error after disturbing the status quo, it removes `config.status'. -4) Look at `./lisp/paths.el'; if some of those values are not right +5) Look at `./lisp/paths.el'; if some of those values are not right for your system, set up the file `./lisp/site-init.el' with XEmacs Lisp code to override them; it is not a good idea to edit paths.el itself. YOU MUST USE THE LISP FUNCTION `setq' TO ASSIGN VALUES, @@ -403,7 +419,7 @@ XEmacs cannot detect, you may need to change the value of `directory-abbrev-alist'. -5) Put into `./lisp/site-init.el' or `./lisp/site-load.el' any Emacs +6) Put into `./lisp/site-init.el' or `./lisp/site-load.el' any Emacs Lisp code you want XEmacs to load before it is dumped out. Use site-load.el for additional libraries if you arrange for their documentation strings to be in the lib-src/DOC file (see @@ -422,12 +438,12 @@ The `site-*.el' files are nonexistent in the distribution. You do not need to create them if you have nothing to put in them. -6) Refer to the file `./etc/TERMS' for information on fields you may +7) Refer to the file `./etc/TERMS' for information on fields you may wish to add to various termcap entries. The files `./etc/termcap.ucb' and `./etc/termcap.dat' may already contain appropriately-modified entries. -7) Run `make' in the top directory of the XEmacs distribution to finish +8) Run `make' in the top directory of the XEmacs distribution to finish building XEmacs in the standard way. The final executable file is named `src/emacs'. You can execute this file "in place" without copying it, if you wish; then it automatically uses the sibling @@ -505,18 +521,18 @@ Using GNU Make allows for simultaneous builds with and without the --srcdir option. -8) If your system uses lock files to interlock access to mailer inbox files, -then you might need to make the movemail program setuid or setgid -to enable it to write the lock files. We believe this is safe. +9) If your system uses lock files to interlock access to mailer inbox +files, then you might need to make the movemail program setuid or +setgid to enable it to write the lock files. We believe this is safe. The setuid/setgid bits need not be set on any other XEmacs-related executables. -9) You are done with the hard part! You can remove executables and +10) You are done with the hard part! You can remove executables and object files from the build directory by typing `make clean'. To also remove the files that `configure' created (so you can compile XEmacs for a different configuration), type `make distclean'. -10) You should now go to the XEmacs web page at http://www.xemacs.org/ +11) You should now go to the XEmacs web page at http://www.xemacs.org/ and decide what additional Lisp support you wish to have. MAKE VARIABLES @@ -670,13 +686,13 @@ `src/config.h', and change the two `#include' directives to include the appropriate system and architecture description files. -2) Edit `./src/config.h' to set the right options for your system. If +3) Edit `./src/config.h' to set the right options for your system. If you need to override any of the definitions in the s/*.h and m/*.h files for your system and machine, do so by editing config.h, not by changing the s/*.h and m/*.h files. Occasionally you may need to redefine parameters used in `./lib-src/movemail.c'. -3) If you're going to use the make utility to build XEmacs, you will +4) If you're going to use the make utility to build XEmacs, you will still need to run `configure' first, giving the appropriate values for the variables in the sections entitled "Things `configure' Might Edit" and "Where To Install Things." Note that you may only need to change @@ -776,6 +792,10 @@ PROBLEMS +The most likely problem is that you forgot to read and follow the +directions in README.packages. You can not have a working XEmacs +without downloading some additional packages. + See the file PROBLEMS in this directory for a list of various problems sometimes encountered, and what to do about them. diff -r 28d9c139be4c -r 11054d720c21 Makefile.in.in --- a/Makefile.in.in Mon Aug 13 11:25:03 2007 +0200 +++ b/Makefile.in.in Mon Aug 13 11:26:11 2007 +0200 @@ -49,6 +49,9 @@ ## make extraclean ## Still more severe - delete backup and autosave files, too. +#define NOT_C_CODE +#include "src/config.h" + #ifdef USE_GNU_MAKE RECURSIVE_MAKE=$(MAKE) #else @@ -199,7 +202,7 @@ ## currently being edited. lockdir=@lockdir@ -# Where to put the DOC file. +## Where to put the DOC file. docdir=@docdir@ ## Where to put executables to be run by XEmacs rather than @@ -224,7 +227,10 @@ MAKE_SUBDIR = @MAKE_SUBDIR@ ## Subdirectories that can be made recursively. -SUBDIR = ${MAKE_SUBDIR} man +SUBDIR = ${MAKE_SUBDIR} man + +## Subdirectories that must be cleaned on distclean +SUBDIR_DISTCLEAN = ${SUBDIR} modules/sample modules/ldap modules/zlib modules/base64 ## The makefiles of the directories in ${MAKE_SUBDIR}. SUBDIR_MAKEFILES = @SUBDIR_MAKEFILES@ @@ -409,9 +415,18 @@ for subdir in `find ${archlibdir} -type d ! -name RCS ! -name SCCS ! -name CVS -print` ; \ do (cd $${subdir} && $(RM) -r RCS CVS SCCS \#* *~) ; done ; \ else true; fi +#ifdef WINDOWSNT + ${INSTALL_PROGRAM} src/${PROGNAME} ${bindir}/${PROGNAME} + -chmod 0755 ${bindir}/${PROGNAME} +#else ${INSTALL_PROGRAM} src/${PROGNAME} ${bindir}/${PROGNAME}-${version} -chmod 0755 ${bindir}/${PROGNAME}-${version} +# ifdef __CYGWIN32__ + cd ${bindir} && $(RM) ./${PROGNAME} && ${LN_S} ${PROGNAME}-${version}.exe ./${PROGNAME} +# else cd ${bindir} && $(RM) ./${PROGNAME} && ${LN_S} ${PROGNAME}-${version} ./${PROGNAME} +# endif /* __CYGWIN32__ */ +#endif /* WINDOWSNT */ if test "${prefix}" != "${exec_prefix}"; then \ for dir in \ lib/${inststaticdir} \ @@ -552,10 +567,10 @@ $(RM) config.status config.log confdefs.h config-tmp-* build-install Installation ; \ $(RM) core .sbinit lock/* GNUmakefile Makefile Makefile.in ; \ $(RM) lisp/finder-inf.el* Installation.el Installation.elc ; \ - $(RM) packages mule-packages site-lisp + $(RM) -r site-packages xemacs-packages mule-packages site-lisp distclean: FRC.distclean - for d in $(SUBDIR); do (cd ./$$d && $(RECURSIVE_MAKE) $@); done + for d in $(SUBDIR_DISTCLEAN); do (cd ./$$d && $(RECURSIVE_MAKE) $@); done -${top_distclean} ## `realclean' diff -r 28d9c139be4c -r 11054d720c21 PROBLEMS --- a/PROBLEMS Mon Aug 13 11:25:03 2007 +0200 +++ b/PROBLEMS Mon Aug 13 11:26:11 2007 +0200 @@ -391,8 +391,8 @@ Marcus Thiessel - Unfortunately, XEmacs releases <21.0 don't work with Motif2.1. It - will compile but you will get excessive X11 errors like + Unfortunately, XEmacs releases prior to 21.0 don't work with + Motif2.1. It will compile but you will get excessive X11 errors like xemacs: X Error of failed request: BadGC (invalid GC parameter) @@ -542,17 +542,23 @@ *** You type Control-H (Backspace) expecting to delete characters. Emacs has traditionally used Control-H for help; unfortunately this -interferes with its use as Backspace on TTY's. One way to solve this -problem is to put this in your .emacs: +interferes with its use as Backspace on TTY's. As of XEmacs 21, +XEmacs looks at the "erase" setting of TTY structures and maps C-h to +backspace when erase is set to C-h. This is sort of a special hack, +but it makes it possible for you to use the standard: + + stty erase ^H - (when (eq tty-erase-char ?\C-h) - (keyboard-translate ?\C-h ?\C-?) - (global-set-key "\M-?" 'help-command)) +to get your backspace key to erase characters. The erase setting is +recorded in the Lisp variable `tty-erase-char', which you can use to +tune the settings in your .emacs. -This checks whether the TTY erase char is C-h, and if it is, makes -Control-H (Backspace) work sensibly, and moves help to Meta-? (ESC ?). +A major drawback of this is that when C-h becomes backspace, it no +longer invokes help. In that case, you need to use f1 for help, or +bind another key. An example of the latter is the following code, +which moves help to Meta-? (ESC ?): -Note that you can probably also access help using F1. + (global-set-key "\M-?" 'help-command) *** Mail agents (VM, Gnus, rmail) cannot get new mail diff -r 28d9c139be4c -r 11054d720c21 README --- a/README Mon Aug 13 11:25:03 2007 +0200 +++ b/README Mon Aug 13 11:26:11 2007 +0200 @@ -16,6 +16,9 @@ See the file `nt/README' for instructions on building XEmacs for Microsoft Windows. +The file 'README.packages' will guide you in the installation of +(essential) add on packages. + Reports of bugs in XEmacs should be posted to the newsgroup comp.emacs.xemacs or sent to the mailing list xemacs@xemacs.org. See the "Bugs" section of the XEmacs manual for more information on how to diff -r 28d9c139be4c -r 11054d720c21 README.packages --- a/README.packages Mon Aug 13 11:25:03 2007 +0200 +++ b/README.packages Mon Aug 13 11:26:11 2007 +0200 @@ -224,3 +224,13 @@ XEmacs no longer looks into a 'site-lisp' directly by default. A good place to put 'site-start.el' would be in $prefix/lib/xemacs/site-packages/lisp/ + +Finding the right packages +-------------------------- + +If you want to find out which package contains the functionality you +are looking for, use M-x package-get-package-provider, and give it a +symbol that is likely to be in that package. eg, if some code you +want to use has a (require 'thingatpt) in it, try doing +M-x package-get-package-provider RET thingatpt , which will return +something like: (fsf-compat "1.06"). diff -r 28d9c139be4c -r 11054d720c21 configure --- a/configure Mon Aug 13 11:25:03 2007 +0200 +++ b/configure Mon Aug 13 11:26:11 2007 +0200 @@ -263,6 +263,7 @@ with_tty="" use_union_type="no" with_dnet="" +pdump="no" @@ -359,6 +360,7 @@ const_is_losing | \ usage_tracking | \ use_union_type | \ + pdump | \ debug | \ use_assertions | \ memory_usage_stats | \ @@ -699,7 +701,9 @@ eval "$opt=\"$val\"" ;; - "run_in_place" | \ + "use_minimal_tagbits" | \ + "use_indexed_lrecord_implementation" | \ + "run_in_place" | \ "with_gnu_make" ) echo "configure: warning: Obsolete option \`--$optname' ignored." 1>&2 ;; @@ -792,7 +796,7 @@ fi echo $ac_n "checking whether ln -s works""... $ac_c" 1>&6 -echo "configure:796: checking whether ln -s works" >&5 +echo "configure:800: checking whether ln -s works" >&5 rm -f conftestdata if ln -s X conftestdata 2>/dev/null @@ -1037,7 +1041,7 @@ echo $ac_n "checking "host system type"""... $ac_c" 1>&6 -echo "configure:1041: checking "host system type"" >&5 +echo "configure:1045: checking "host system type"" >&5 internal_configuration=`echo $configuration | sed 's/-\(workshop\)//'` canonical=`${CONFIG_SHELL-/bin/sh} $srcdir/config.sub "$internal_configuration"` configuration=`echo "$configuration" | sed 's/^\([^-][^-]*-[^-][^-]*-[^-][^-]*\)-.*$/\1/'` @@ -1056,6 +1060,7 @@ vax-*-* ) machine=vax ;; mips-dec-* ) machine=pmax ;; mips-sgi-* ) machine=iris4d ;; + mips*-linux ) machine=mips ;; romp-ibm-* ) machine=ibmrt ;; rs6000-ibm-aix* ) machine=ibmrs6000 ;; powerpc-ibm-aix* ) machine=ibmrs6000 ;; @@ -1530,7 +1535,7 @@ # Extract the first word of "gcc", so it can be a program name with args. set dummy gcc; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1534: checking for $ac_word" >&5 +echo "configure:1539: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -1557,7 +1562,7 @@ # Extract the first word of "cc", so it can be a program name with args. set dummy cc; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1561: checking for $ac_word" >&5 +echo "configure:1566: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -1605,7 +1610,7 @@ # Extract the first word of "cl", so it can be a program name with args. set dummy cl; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1609: checking for $ac_word" >&5 +echo "configure:1614: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -1634,7 +1639,7 @@ fi echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6 -echo "configure:1638: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 +echo "configure:1643: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 ac_ext=c xe_cppflags='$CPPFLAGS $c_switch_site $c_switch_machine $c_switch_system $c_switch_x_site $X_CFLAGS' @@ -1647,12 +1652,12 @@ cat > conftest.$ac_ext << EOF -#line 1651 "configure" +#line 1656 "configure" #include "confdefs.h" main(){return(0);} EOF -if { (eval echo configure:1656: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:1661: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then ac_cv_prog_cc_works=yes # If we can't run a trivial program, we are probably using a cross compiler. if (./conftest; exit) 2>/dev/null; then @@ -1680,19 +1685,19 @@ { echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; } fi echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6 -echo "configure:1684: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 +echo "configure:1689: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6 cross_compiling=$ac_cv_prog_cc_cross echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6 -echo "configure:1689: checking whether we are using GNU C" >&5 +echo "configure:1694: checking whether we are using GNU C" >&5 cat > conftest.c <&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then +if { ac_try='${CC-cc} -E conftest.c'; { (eval echo configure:1701: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then ac_cv_prog_gcc=yes else ac_cv_prog_gcc=no @@ -1710,7 +1715,7 @@ ac_save_CFLAGS="$CFLAGS" CFLAGS= echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 -echo "configure:1714: checking whether ${CC-cc} accepts -g" >&5 +echo "configure:1719: checking whether ${CC-cc} accepts -g" >&5 echo 'void f(){}' > conftest.c if test -z "`${CC-cc} -g -c conftest.c 2>&1`"; then @@ -1743,7 +1748,7 @@ # Extract the first word of "gcc", so it can be a program name with args. set dummy gcc; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1747: checking for $ac_word" >&5 +echo "configure:1752: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -1770,7 +1775,7 @@ # Extract the first word of "cc", so it can be a program name with args. set dummy cc; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1774: checking for $ac_word" >&5 +echo "configure:1779: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -1818,7 +1823,7 @@ # Extract the first word of "cl", so it can be a program name with args. set dummy cl; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1822: checking for $ac_word" >&5 +echo "configure:1827: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -1847,7 +1852,7 @@ fi echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6 -echo "configure:1851: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 +echo "configure:1856: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 ac_ext=c xe_cppflags='$CPPFLAGS $c_switch_site $c_switch_machine $c_switch_system $c_switch_x_site $X_CFLAGS' @@ -1860,12 +1865,12 @@ cat > conftest.$ac_ext << EOF -#line 1864 "configure" +#line 1869 "configure" #include "confdefs.h" main(){return(0);} EOF -if { (eval echo configure:1869: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:1874: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then ac_cv_prog_cc_works=yes # If we can't run a trivial program, we are probably using a cross compiler. if (./conftest; exit) 2>/dev/null; then @@ -1893,19 +1898,19 @@ { echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; } fi echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6 -echo "configure:1897: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 +echo "configure:1902: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6 cross_compiling=$ac_cv_prog_cc_cross echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6 -echo "configure:1902: checking whether we are using GNU C" >&5 +echo "configure:1907: checking whether we are using GNU C" >&5 cat > conftest.c <&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then +if { ac_try='${CC-cc} -E conftest.c'; { (eval echo configure:1914: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then ac_cv_prog_gcc=yes else ac_cv_prog_gcc=no @@ -1923,7 +1928,7 @@ ac_save_CFLAGS="$CFLAGS" CFLAGS= echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 -echo "configure:1927: checking whether ${CC-cc} accepts -g" >&5 +echo "configure:1932: checking whether ${CC-cc} accepts -g" >&5 echo 'void f(){}' > conftest.c if test -z "`${CC-cc} -g -c conftest.c 2>&1`"; then @@ -1956,7 +1961,7 @@ # Extract the first word of "gcc", so it can be a program name with args. set dummy gcc; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1960: checking for $ac_word" >&5 +echo "configure:1965: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -1983,7 +1988,7 @@ # Extract the first word of "cc", so it can be a program name with args. set dummy cc; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1987: checking for $ac_word" >&5 +echo "configure:1992: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -2031,7 +2036,7 @@ # Extract the first word of "cl", so it can be a program name with args. set dummy cl; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:2035: checking for $ac_word" >&5 +echo "configure:2040: checking for $ac_word" >&5 if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. @@ -2060,7 +2065,7 @@ fi echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6 -echo "configure:2064: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 +echo "configure:2069: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 ac_ext=c xe_cppflags='$CPPFLAGS $c_switch_site $c_switch_machine $c_switch_system $c_switch_x_site $X_CFLAGS' @@ -2073,12 +2078,12 @@ cat > conftest.$ac_ext << EOF -#line 2077 "configure" +#line 2082 "configure" #include "confdefs.h" main(){return(0);} EOF -if { (eval echo configure:2082: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:2087: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then ac_cv_prog_cc_works=yes # If we can't run a trivial program, we are probably using a cross compiler. if (./conftest; exit) 2>/dev/null; then @@ -2106,19 +2111,19 @@ { echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; } fi echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6 -echo "configure:2110: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 +echo "configure:2115: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6 cross_compiling=$ac_cv_prog_cc_cross echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6 -echo "configure:2115: checking whether we are using GNU C" >&5 +echo "configure:2120: checking whether we are using GNU C" >&5 cat > conftest.c <&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then +if { ac_try='${CC-cc} -E conftest.c'; { (eval echo configure:2127: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then ac_cv_prog_gcc=yes else ac_cv_prog_gcc=no @@ -2136,7 +2141,7 @@ ac_save_CFLAGS="$CFLAGS" CFLAGS= echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 -echo "configure:2140: checking whether ${CC-cc} accepts -g" >&5 +echo "configure:2145: checking whether ${CC-cc} accepts -g" >&5 echo 'void f(){}' > conftest.c if test -z "`${CC-cc} -g -c conftest.c 2>&1`"; then @@ -2173,7 +2178,7 @@ test -n "$NON_GNU_CPP" -a "$GCC" != "yes" -a -z "$CPP" && CPP="$NON_GNU_CPP" echo $ac_n "checking how to run the C preprocessor""... $ac_c" 1>&6 -echo "configure:2177: checking how to run the C preprocessor" >&5 +echo "configure:2182: checking how to run the C preprocessor" >&5 # On Suns, sometimes $CPP names a directory. if test -n "$CPP" && test -d "$CPP"; then CPP= @@ -2186,13 +2191,13 @@ # On the NeXT, cc -E runs the code through the compiler's parser, # not just through cpp. cat > conftest.$ac_ext < Syntax Error EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2196: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:2201: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then : @@ -2203,13 +2208,13 @@ rm -rf conftest* CPP="${CC-cc} -E -traditional-cpp" cat > conftest.$ac_ext < Syntax Error EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2213: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:2218: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then : @@ -2220,13 +2225,13 @@ rm -rf conftest* CPP="${CC-cc} -nologo -E" cat > conftest.$ac_ext < Syntax Error EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2230: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:2235: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then : @@ -2251,9 +2256,9 @@ echo $ac_n "checking for AIX""... $ac_c" 1>&6 -echo "configure:2255: checking for AIX" >&5 -cat > conftest.$ac_ext <&5 +cat > conftest.$ac_ext <&6 -echo "configure:2284: checking for GNU libc" >&5 -cat > conftest.$ac_ext <&5 +cat > conftest.$ac_ext < int main() { @@ -2294,7 +2299,7 @@ ; return 0; } EOF -if { (eval echo configure:2298: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:2303: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* have_glibc=yes else @@ -2316,7 +2321,7 @@ cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:2337: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then : else @@ -2602,7 +2607,7 @@ fi echo $ac_n "checking for dynodump""... $ac_c" 1>&6 -echo "configure:2606: checking for dynodump" >&5 +echo "configure:2611: checking for dynodump" >&5 if test "$unexec" != "unexsol2.o"; then echo "$ac_t""no" 1>&6 else @@ -2640,12 +2645,12 @@ done echo $ac_n "checking for terminateAndUnload in -lC""... $ac_c" 1>&6 -echo "configure:2644: checking for terminateAndUnload in -lC" >&5 +echo "configure:2649: checking for terminateAndUnload in -lC" >&5 ac_lib_var=`echo C'_'terminateAndUnload | sed 'y%./+-%__p_%'` xe_check_libs=" -lC " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:2665: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -2760,7 +2765,7 @@ if test "$add_runtime_path" = "yes"; then echo $ac_n "checking "for runtime libraries flag"""... $ac_c" 1>&6 -echo "configure:2764: checking "for runtime libraries flag"" >&5 +echo "configure:2769: checking "for runtime libraries flag"" >&5 case "$opsys" in sol2 ) dash_r="-R" ;; decosf* | linux* | irix*) dash_r="-rpath " ;; @@ -2782,14 +2787,14 @@ done fi cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +#line 2791 "configure" +#include "confdefs.h" + +int main() { + +; return 0; } +EOF +if { (eval echo configure:2798: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* dash_r="$try_dash_r" else @@ -2891,10 +2896,10 @@ fi after_morecore_hook_exists=yes echo $ac_n "checking for malloc_get_state""... $ac_c" 1>&6 -echo "configure:2895: checking for malloc_get_state" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:2926: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_malloc_get_state=yes" else @@ -2937,10 +2942,10 @@ fi echo $ac_n "checking for malloc_set_state""... $ac_c" 1>&6 -echo "configure:2941: checking for malloc_set_state" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:2972: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_malloc_set_state=yes" else @@ -2983,16 +2988,16 @@ fi echo $ac_n "checking whether __after_morecore_hook exists""... $ac_c" 1>&6 -echo "configure:2987: checking whether __after_morecore_hook exists" >&5 -cat > conftest.$ac_ext <&5 +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3001: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* echo "$ac_t""yes" 1>&6 else @@ -3051,7 +3056,7 @@ # Extract the first word of "ranlib", so it can be a program name with args. set dummy ranlib; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:3055: checking for $ac_word" >&5 +echo "configure:3060: checking for $ac_word" >&5 if test -n "$RANLIB"; then ac_cv_prog_RANLIB="$RANLIB" # Let the user override the test. @@ -3106,7 +3111,7 @@ # SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" # ./install, which can be erroneously created by make from ./install.sh. echo $ac_n "checking for a BSD compatible install""... $ac_c" 1>&6 -echo "configure:3110: checking for a BSD compatible install" >&5 +echo "configure:3115: checking for a BSD compatible install" >&5 if test -z "$INSTALL"; then IFS="${IFS= }"; ac_save_IFS="$IFS"; IFS=":" @@ -3160,7 +3165,7 @@ # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:3164: checking for $ac_word" >&5 +echo "configure:3169: checking for $ac_word" >&5 if test -n "$YACC"; then ac_cv_prog_YACC="$YACC" # Let the user override the test. @@ -3192,15 +3197,15 @@ do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3196: checking for $ac_hdr" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3204: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3209: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3233,15 +3238,15 @@ do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3237: checking for $ac_hdr" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3245: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3250: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3274,15 +3279,15 @@ do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3278: checking for $ac_hdr" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3286: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3291: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3312,10 +3317,10 @@ done echo $ac_n "checking for sys/wait.h that is POSIX.1 compatible""... $ac_c" 1>&6 -echo "configure:3316: checking for sys/wait.h that is POSIX.1 compatible" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #include @@ -3331,7 +3336,7 @@ s = WIFEXITED (s) ? WEXITSTATUS (s) : 1; ; return 0; } EOF -if { (eval echo configure:3335: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3340: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_header_sys_wait_h=yes else @@ -3355,10 +3360,10 @@ fi echo $ac_n "checking for ANSI C header files""... $ac_c" 1>&6 -echo "configure:3359: checking for ANSI C header files" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #include @@ -3366,7 +3371,7 @@ #include EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3370: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3375: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3383,7 +3388,7 @@ if test $ac_cv_header_stdc = yes; then # SunOS 4.x string.h does not declare mem*, contrary to ANSI. cat > conftest.$ac_ext < EOF @@ -3401,7 +3406,7 @@ if test $ac_cv_header_stdc = yes; then # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. cat > conftest.$ac_ext < EOF @@ -3419,7 +3424,7 @@ if test $ac_cv_header_stdc = yes; then # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi. cat > conftest.$ac_ext < #define ISLOWER(c) ('a' <= (c) && (c) <= 'z') @@ -3430,7 +3435,7 @@ exit (0); } EOF -if { (eval echo configure:3434: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:3439: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then : else @@ -3456,10 +3461,10 @@ fi echo $ac_n "checking whether time.h and sys/time.h may both be included""... $ac_c" 1>&6 -echo "configure:3460: checking whether time.h and sys/time.h may both be included" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #include @@ -3468,7 +3473,7 @@ struct tm *tp; ; return 0; } EOF -if { (eval echo configure:3472: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3477: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_header_time=yes else @@ -3492,10 +3497,10 @@ fi echo $ac_n "checking for sys_siglist declaration in signal.h or unistd.h""... $ac_c" 1>&6 -echo "configure:3496: checking for sys_siglist declaration in signal.h or unistd.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #include @@ -3507,7 +3512,7 @@ char *msg = *(sys_siglist + 1); ; return 0; } EOF -if { (eval echo configure:3511: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3516: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_decl_sys_siglist=yes else @@ -3532,9 +3537,9 @@ echo $ac_n "checking for struct utimbuf""... $ac_c" 1>&6 -echo "configure:3536: checking for struct utimbuf" >&5 -cat > conftest.$ac_ext <&5 +cat > conftest.$ac_ext < @@ -3553,7 +3558,7 @@ static struct utimbuf x; x.actime = x.modtime; ; return 0; } EOF -if { (eval echo configure:3557: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3562: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* echo "$ac_t""yes" 1>&6 { test "$extra_verbose" = "yes" && cat << \EOF @@ -3573,10 +3578,10 @@ rm -f conftest* echo $ac_n "checking return type of signal handlers""... $ac_c" 1>&6 -echo "configure:3577: checking return type of signal handlers" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #include @@ -3593,7 +3598,7 @@ int i; ; return 0; } EOF -if { (eval echo configure:3597: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3602: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_type_signal=void else @@ -3615,10 +3620,10 @@ echo $ac_n "checking for size_t""... $ac_c" 1>&6 -echo "configure:3619: checking for size_t" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #if STDC_HEADERS @@ -3649,10 +3654,10 @@ fi echo $ac_n "checking for pid_t""... $ac_c" 1>&6 -echo "configure:3653: checking for pid_t" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #if STDC_HEADERS @@ -3683,10 +3688,10 @@ fi echo $ac_n "checking for uid_t in sys/types.h""... $ac_c" 1>&6 -echo "configure:3687: checking for uid_t in sys/types.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF @@ -3722,10 +3727,10 @@ fi echo $ac_n "checking for mode_t""... $ac_c" 1>&6 -echo "configure:3726: checking for mode_t" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #if STDC_HEADERS @@ -3756,10 +3761,10 @@ fi echo $ac_n "checking for off_t""... $ac_c" 1>&6 -echo "configure:3760: checking for off_t" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #if STDC_HEADERS @@ -3791,9 +3796,9 @@ echo $ac_n "checking for struct timeval""... $ac_c" 1>&6 -echo "configure:3795: checking for struct timeval" >&5 -cat > conftest.$ac_ext <&5 +cat > conftest.$ac_ext < @@ -3809,7 +3814,7 @@ static struct timeval x; x.tv_sec = x.tv_usec; ; return 0; } EOF -if { (eval echo configure:3813: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3818: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* echo "$ac_t""yes" 1>&6 HAVE_TIMEVAL=yes @@ -3831,10 +3836,10 @@ rm -f conftest* echo $ac_n "checking whether struct tm is in sys/time.h or time.h""... $ac_c" 1>&6 -echo "configure:3835: checking whether struct tm is in sys/time.h or time.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #include @@ -3842,7 +3847,7 @@ struct tm *tp; tp->tm_sec; ; return 0; } EOF -if { (eval echo configure:3846: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3851: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_struct_tm=time.h else @@ -3866,10 +3871,10 @@ fi echo $ac_n "checking for tm_zone in struct tm""... $ac_c" 1>&6 -echo "configure:3870: checking for tm_zone in struct tm" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #include <$ac_cv_struct_tm> @@ -3877,7 +3882,7 @@ struct tm tm; tm.tm_zone; ; return 0; } EOF -if { (eval echo configure:3881: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3886: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_struct_tm_zone=yes else @@ -3900,10 +3905,10 @@ else echo $ac_n "checking for tzname""... $ac_c" 1>&6 -echo "configure:3904: checking for tzname" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < #ifndef tzname /* For SGI. */ @@ -3913,7 +3918,7 @@ atoi(*tzname); ; return 0; } EOF -if { (eval echo configure:3917: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3922: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_var_tzname=yes else @@ -3939,10 +3944,10 @@ echo $ac_n "checking for working const""... $ac_c" 1>&6 -echo "configure:3943: checking for working const" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4000: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_const=yes else @@ -4016,7 +4021,7 @@ echo $ac_n "checking whether ${MAKE-make} sets \${MAKE}""... $ac_c" 1>&6 -echo "configure:4020: checking whether ${MAKE-make} sets \${MAKE}" >&5 +echo "configure:4025: checking whether ${MAKE-make} sets \${MAKE}" >&5 set dummy ${MAKE-make}; ac_make=`echo "$2" | sed 'y%./+-%__p_%'` cat > conftestmake <<\EOF @@ -4041,12 +4046,12 @@ echo $ac_n "checking whether byte ordering is bigendian""... $ac_c" 1>&6 -echo "configure:4045: checking whether byte ordering is bigendian" >&5 +echo "configure:4050: checking whether byte ordering is bigendian" >&5 ac_cv_c_bigendian=unknown # See if sys/param.h defines the BYTE_ORDER macro. cat > conftest.$ac_ext < #include @@ -4057,11 +4062,11 @@ #endif ; return 0; } EOF -if { (eval echo configure:4061: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4066: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* # It does; now see whether it defined to BIG_ENDIAN or not. cat > conftest.$ac_ext < #include @@ -4072,7 +4077,7 @@ #endif ; return 0; } EOF -if { (eval echo configure:4076: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4081: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_bigendian=yes else @@ -4089,7 +4094,7 @@ rm -f conftest* if test $ac_cv_c_bigendian = unknown; then cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:4111: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_c_bigendian=no else @@ -4129,10 +4134,10 @@ echo $ac_n "checking size of short""... $ac_c" 1>&6 -echo "configure:4133: checking size of short" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < main() @@ -4143,7 +4148,7 @@ exit(0); } EOF -if { (eval echo configure:4147: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:4152: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_sizeof_short=`cat conftestval` else @@ -4171,10 +4176,10 @@ exit 1 fi echo $ac_n "checking size of int""... $ac_c" 1>&6 -echo "configure:4175: checking size of int" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < main() @@ -4185,7 +4190,7 @@ exit(0); } EOF -if { (eval echo configure:4189: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:4194: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_sizeof_int=`cat conftestval` else @@ -4207,10 +4212,10 @@ echo $ac_n "checking size of long""... $ac_c" 1>&6 -echo "configure:4211: checking size of long" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < main() @@ -4221,7 +4226,7 @@ exit(0); } EOF -if { (eval echo configure:4225: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:4230: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_sizeof_long=`cat conftestval` else @@ -4243,10 +4248,10 @@ echo $ac_n "checking size of long long""... $ac_c" 1>&6 -echo "configure:4247: checking size of long long" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < main() @@ -4257,7 +4262,7 @@ exit(0); } EOF -if { (eval echo configure:4261: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:4266: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_sizeof_long_long=`cat conftestval` else @@ -4279,10 +4284,10 @@ echo $ac_n "checking size of void *""... $ac_c" 1>&6 -echo "configure:4283: checking size of void *" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < main() @@ -4293,7 +4298,7 @@ exit(0); } EOF -if { (eval echo configure:4297: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:4302: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_sizeof_void_p=`cat conftestval` else @@ -4316,7 +4321,7 @@ echo $ac_n "checking for long file names""... $ac_c" 1>&6 -echo "configure:4320: checking for long file names" >&5 +echo "configure:4325: checking for long file names" >&5 ac_cv_sys_long_file_names=yes # Test for long file names in all the places we know might matter: @@ -4362,10 +4367,10 @@ echo $ac_n "checking for sin""... $ac_c" 1>&6 -echo "configure:4366: checking for sin" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4397: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_sin=yes" else @@ -4406,12 +4411,12 @@ echo "$ac_t""no" 1>&6 echo $ac_n "checking for sin in -lm""... $ac_c" 1>&6 -echo "configure:4410: checking for sin in -lm" >&5 +echo "configure:4415: checking for sin in -lm" >&5 ac_lib_var=`echo m'_'sin | sed 'y%./+-%__p_%'` xe_check_libs=" -lm " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4431: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4466,14 +4471,14 @@ cat > conftest.$ac_ext < int main() { return atanh(1.0) + asinh(1.0) + acosh(1.0); ; return 0; } EOF -if { (eval echo configure:4477: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4482: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* { test "$extra_verbose" = "yes" && cat << \EOF Defining HAVE_INVERSE_HYPERBOLIC @@ -4490,7 +4495,7 @@ rm -f conftest* echo "checking type of mail spool file locking" 1>&6 -echo "configure:4494: checking type of mail spool file locking" >&5 +echo "configure:4499: checking type of mail spool file locking" >&5 test -z "$mail_locking" -a "$mail_use_flock" = "yes" && mail_locking=flock test -z "$mail_locking" -a "$mail_use_lockf" = "yes" && mail_locking=lockf if test "$mail_locking" = "lockf"; then { test "$extra_verbose" = "yes" && cat << \EOF @@ -4515,12 +4520,12 @@ case "$opsys" in decosf*) echo $ac_n "checking for cma_open in -lpthreads""... $ac_c" 1>&6 -echo "configure:4519: checking for cma_open in -lpthreads" >&5 +echo "configure:4524: checking for cma_open in -lpthreads" >&5 ac_lib_var=`echo pthreads'_'cma_open | sed 'y%./+-%__p_%'` xe_check_libs=" -lpthreads " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4540: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4567,7 +4572,7 @@ esac echo $ac_n "checking whether the -xildoff compiler flag is required""... $ac_c" 1>&6 -echo "configure:4571: checking whether the -xildoff compiler flag is required" >&5 +echo "configure:4576: checking whether the -xildoff compiler flag is required" >&5 if ${CC-cc} '-###' -xildon no_such_file.c 2>&1 | grep '^[^ ]*/ild ' > /dev/null ; then if ${CC-cc} '-###' -xildoff no_such_file.c 2>&1 | grep '^[^ ]*/ild ' > /dev/null ; then echo "$ac_t""no" 1>&6; @@ -4578,7 +4583,7 @@ if test "$opsys" = "sol2" && test "$OS_RELEASE" -ge 56; then echo $ac_n "checking for \"-z ignore\" linker flag""... $ac_c" 1>&6 -echo "configure:4582: checking for \"-z ignore\" linker flag" >&5 +echo "configure:4587: checking for \"-z ignore\" linker flag" >&5 case "`ld -h 2>&1`" in *-z\ ignore\|record* ) echo "$ac_t""yes" 1>&6 ld_switch_site="-z ignore $ld_switch_site" && if test "$extra_verbose" = "yes"; then echo " Prepending \"-z ignore\" to \$ld_switch_site"; fi ;; @@ -4588,7 +4593,7 @@ echo "checking "for specified window system"" 1>&6 -echo "configure:4592: checking "for specified window system"" >&5 +echo "configure:4597: checking "for specified window system"" >&5 if test "$with_x11" != "no"; then test "$x_includes $x_libraries" != "NONE NONE" && \ @@ -4621,7 +4626,7 @@ # Uses ac_ vars as temps to allow command line to override cache and checks. # --without-x overrides everything else, but does not touch the cache. echo $ac_n "checking for X""... $ac_c" 1>&6 -echo "configure:4625: checking for X" >&5 +echo "configure:4630: checking for X" >&5 # Check whether --with-x or --without-x was given. if test "${with_x+set}" = set; then @@ -4681,12 +4686,12 @@ # First, try using that file with no special directory specified. cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:4690: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:4695: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -4755,14 +4760,14 @@ ac_save_LIBS="$LIBS" LIBS="-l$x_direct_test_library $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4771: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* LIBS="$ac_save_LIBS" # We can link X programs with no special library path. @@ -4871,17 +4876,17 @@ case "`(uname -sr) 2>/dev/null`" in "SunOS 5"*) echo $ac_n "checking whether -R must be followed by a space""... $ac_c" 1>&6 -echo "configure:4875: checking whether -R must be followed by a space" >&5 +echo "configure:4880: checking whether -R must be followed by a space" >&5 ac_xsave_LIBS="$LIBS"; LIBS="$LIBS -R$x_libraries" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +#line 4883 "configure" +#include "confdefs.h" + +int main() { + +; return 0; } +EOF +if { (eval echo configure:4890: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_R_nospace=yes else @@ -4897,14 +4902,14 @@ else LIBS="$ac_xsave_LIBS -R $x_libraries" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +#line 4906 "configure" +#include "confdefs.h" + +int main() { + +; return 0; } +EOF +if { (eval echo configure:4913: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_R_space=yes else @@ -4940,12 +4945,12 @@ else echo $ac_n "checking for dnet_ntoa in -ldnet""... $ac_c" 1>&6 -echo "configure:4944: checking for dnet_ntoa in -ldnet" >&5 +echo "configure:4949: checking for dnet_ntoa in -ldnet" >&5 ac_lib_var=`echo dnet'_'dnet_ntoa | sed 'y%./+-%__p_%'` xe_check_libs=" -ldnet " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4965: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4980,12 +4985,12 @@ if test $ac_cv_lib_dnet_dnet_ntoa = no; then echo $ac_n "checking for dnet_ntoa in -ldnet_stub""... $ac_c" 1>&6 -echo "configure:4984: checking for dnet_ntoa in -ldnet_stub" >&5 +echo "configure:4989: checking for dnet_ntoa in -ldnet_stub" >&5 ac_lib_var=`echo dnet_stub'_'dnet_ntoa | sed 'y%./+-%__p_%'` xe_check_libs=" -ldnet_stub " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5005: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5025,10 +5030,10 @@ # The nsl library prevents programs from opening the X display # on Irix 5.2, according to dickey@clark.net. echo $ac_n "checking for gethostbyname""... $ac_c" 1>&6 -echo "configure:5029: checking for gethostbyname" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5060: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_gethostbyname=yes" else @@ -5072,12 +5077,12 @@ if test $ac_cv_func_gethostbyname = no; then echo $ac_n "checking for gethostbyname in -lnsl""... $ac_c" 1>&6 -echo "configure:5076: checking for gethostbyname in -lnsl" >&5 +echo "configure:5081: checking for gethostbyname in -lnsl" >&5 ac_lib_var=`echo nsl'_'gethostbyname | sed 'y%./+-%__p_%'` xe_check_libs=" -lnsl " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5097: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5118,10 +5123,10 @@ # -lsocket must be given before -lnsl if both are needed. # We assume that if connect needs -lnsl, so does gethostbyname. echo $ac_n "checking for connect""... $ac_c" 1>&6 -echo "configure:5122: checking for connect" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5153: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_connect=yes" else @@ -5167,12 +5172,12 @@ xe_msg_checking="for connect in -lsocket" test -n "$X_EXTRA_LIBS" && xe_msg_checking="$xe_msg_checking using extra libs $X_EXTRA_LIBS" echo $ac_n "checking "$xe_msg_checking"""... $ac_c" 1>&6 -echo "configure:5171: checking "$xe_msg_checking"" >&5 +echo "configure:5176: checking "$xe_msg_checking"" >&5 ac_lib_var=`echo socket'_'connect | sed 'y%./+-%__p_%'` xe_check_libs=" -lsocket $X_EXTRA_LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5192: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5207,10 +5212,10 @@ # gomez@mi.uni-erlangen.de says -lposix is necessary on A/UX. echo $ac_n "checking for remove""... $ac_c" 1>&6 -echo "configure:5211: checking for remove" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5242: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_remove=yes" else @@ -5254,12 +5259,12 @@ if test $ac_cv_func_remove = no; then echo $ac_n "checking for remove in -lposix""... $ac_c" 1>&6 -echo "configure:5258: checking for remove in -lposix" >&5 +echo "configure:5263: checking for remove in -lposix" >&5 ac_lib_var=`echo posix'_'remove | sed 'y%./+-%__p_%'` xe_check_libs=" -lposix " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5279: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5294,10 +5299,10 @@ # BSDI BSD/OS 2.1 needs -lipc for XOpenDisplay. echo $ac_n "checking for shmat""... $ac_c" 1>&6 -echo "configure:5298: checking for shmat" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5329: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_shmat=yes" else @@ -5341,12 +5346,12 @@ if test $ac_cv_func_shmat = no; then echo $ac_n "checking for shmat in -lipc""... $ac_c" 1>&6 -echo "configure:5345: checking for shmat in -lipc" >&5 +echo "configure:5350: checking for shmat in -lipc" >&5 ac_lib_var=`echo ipc'_'shmat | sed 'y%./+-%__p_%'` xe_check_libs=" -lipc " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5366: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5393,12 +5398,12 @@ xe_msg_checking="for IceConnectionNumber in -lICE" test -n "$X_EXTRA_LIBS" && xe_msg_checking="$xe_msg_checking using extra libs $X_EXTRA_LIBS" echo $ac_n "checking "$xe_msg_checking"""... $ac_c" 1>&6 -echo "configure:5397: checking "$xe_msg_checking"" >&5 +echo "configure:5402: checking "$xe_msg_checking"" >&5 ac_lib_var=`echo ICE'_'IceConnectionNumber | sed 'y%./+-%__p_%'` xe_check_libs=" -lICE $X_EXTRA_LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5418: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5578,7 +5583,7 @@ echo "checking for X defines extracted by xmkmf" 1>&6 -echo "configure:5582: checking for X defines extracted by xmkmf" >&5 +echo "configure:5587: checking for X defines extracted by xmkmf" >&5 rm -fr conftestdir if mkdir conftestdir; then cd conftestdir @@ -5610,15 +5615,15 @@ ac_safe=`echo "X11/Intrinsic.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for X11/Intrinsic.h""... $ac_c" 1>&6 -echo "configure:5614: checking for X11/Intrinsic.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:5622: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:5627: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -5642,12 +5647,12 @@ echo $ac_n "checking for XOpenDisplay in -lX11""... $ac_c" 1>&6 -echo "configure:5646: checking for XOpenDisplay in -lX11" >&5 +echo "configure:5651: checking for XOpenDisplay in -lX11" >&5 ac_lib_var=`echo X11'_'XOpenDisplay | sed 'y%./+-%__p_%'` xe_check_libs=" -lX11 " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5667: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5683,12 +5688,12 @@ xe_msg_checking="for XGetFontProperty in -lX11" test -n "-b i486-linuxaout" && xe_msg_checking="$xe_msg_checking using extra libs -b i486-linuxaout" echo $ac_n "checking "$xe_msg_checking"""... $ac_c" 1>&6 -echo "configure:5687: checking "$xe_msg_checking"" >&5 +echo "configure:5692: checking "$xe_msg_checking"" >&5 ac_lib_var=`echo X11'_'XGetFontProperty | sed 'y%./+-%__p_%'` xe_check_libs=" -lX11 -b i486-linuxaout" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5708: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5726,12 +5731,12 @@ echo $ac_n "checking for XShapeSelectInput in -lXext""... $ac_c" 1>&6 -echo "configure:5730: checking for XShapeSelectInput in -lXext" >&5 +echo "configure:5735: checking for XShapeSelectInput in -lXext" >&5 ac_lib_var=`echo Xext'_'XShapeSelectInput | sed 'y%./+-%__p_%'` xe_check_libs=" -lXext " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5751: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5765,12 +5770,12 @@ echo $ac_n "checking for XtOpenDisplay in -lXt""... $ac_c" 1>&6 -echo "configure:5769: checking for XtOpenDisplay in -lXt" >&5 +echo "configure:5774: checking for XtOpenDisplay in -lXt" >&5 ac_lib_var=`echo Xt'_'XtOpenDisplay | sed 'y%./+-%__p_%'` xe_check_libs=" -lXt " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5790: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5804,14 +5809,14 @@ echo $ac_n "checking the version of X11 being used""... $ac_c" 1>&6 -echo "configure:5808: checking the version of X11 being used" >&5 +echo "configure:5813: checking the version of X11 being used" >&5 cat > conftest.$ac_ext < int main(int c, char *v[]) { return c>1 ? XlibSpecificationRelease : 0; } EOF -if { (eval echo configure:5815: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:5820: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ./conftest foobar; x11_release=$? else @@ -5836,15 +5841,15 @@ do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:5840: checking for $ac_hdr" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:5848: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:5853: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -5875,7 +5880,7 @@ echo $ac_n "checking for XFree86""... $ac_c" 1>&6 -echo "configure:5879: checking for XFree86" >&5 +echo "configure:5884: checking for XFree86" >&5 if test -d "/usr/X386/include" -o \ -f "/etc/XF86Config" -o \ -f "/etc/X11/XF86Config" -o \ @@ -5895,12 +5900,12 @@ test -z "$with_xmu" && { echo $ac_n "checking for XmuReadBitmapDataFromFile in -lXmu""... $ac_c" 1>&6 -echo "configure:5899: checking for XmuReadBitmapDataFromFile in -lXmu" >&5 +echo "configure:5904: checking for XmuReadBitmapDataFromFile in -lXmu" >&5 ac_lib_var=`echo Xmu'_'XmuReadBitmapDataFromFile | sed 'y%./+-%__p_%'` xe_check_libs=" -lXmu " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5920: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5950,19 +5955,19 @@ echo $ac_n "checking for main in -lXbsd""... $ac_c" 1>&6 -echo "configure:5954: checking for main in -lXbsd" >&5 +echo "configure:5959: checking for main in -lXbsd" >&5 ac_lib_var=`echo Xbsd'_'main | sed 'y%./+-%__p_%'` xe_check_libs=" -lXbsd " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5971: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -5999,22 +6004,22 @@ fi if test "$with_msw" != "no"; then echo "checking for MS-Windows" 1>&6 -echo "configure:6003: checking for MS-Windows" >&5 +echo "configure:6008: checking for MS-Windows" >&5 echo $ac_n "checking for main in -lgdi32""... $ac_c" 1>&6 -echo "configure:6006: checking for main in -lgdi32" >&5 +echo "configure:6011: checking for main in -lgdi32" >&5 ac_lib_var=`echo gdi32'_'main | sed 'y%./+-%__p_%'` xe_check_libs=" -lgdi32 " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6023: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -6080,12 +6085,12 @@ fi fi cat > conftest.$ac_ext < int main() { return (open("/dev/windows", O_RDONLY, 0) > 0)? 0 : 1; } EOF -if { (eval echo configure:6089: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:6094: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then { test "$extra_verbose" = "yes" && cat << \EOF Defining HAVE_MSG_SELECT @@ -6161,7 +6166,7 @@ esac echo "checking for WM_COMMAND option" 1>&6 -echo "configure:6165: checking for WM_COMMAND option" >&5; +echo "configure:6170: checking for WM_COMMAND option" >&5; if test "$with_wmcommand" != "no"; then { test "$extra_verbose" = "yes" && cat << \EOF Defining HAVE_WMCOMMAND @@ -6176,15 +6181,15 @@ test -z "$with_xauth" && test "$window_system" = "none" && with_xauth=no test -z "$with_xauth" && { ac_safe=`echo "X11/Xauth.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for X11/Xauth.h""... $ac_c" 1>&6 -echo "configure:6180: checking for X11/Xauth.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:6188: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:6193: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -6207,12 +6212,12 @@ } test -z "$with_xauth" && { echo $ac_n "checking for XauGetAuthByAddr in -lXau""... $ac_c" 1>&6 -echo "configure:6211: checking for XauGetAuthByAddr in -lXau" >&5 +echo "configure:6216: checking for XauGetAuthByAddr in -lXau" >&5 ac_lib_var=`echo Xau'_'XauGetAuthByAddr | sed 'y%./+-%__p_%'` xe_check_libs=" -lXau " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6232: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -6268,15 +6273,15 @@ for dir in "" "Tt/" "desktop/" ; do ac_safe=`echo "${dir}tt_c.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for ${dir}tt_c.h""... $ac_c" 1>&6 -echo "configure:6272: checking for ${dir}tt_c.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:6280: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:6285: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -6312,12 +6317,12 @@ xe_msg_checking="for tt_message_create in -ltt" test -n "$extra_libs" && xe_msg_checking="$xe_msg_checking using extra libs $extra_libs" echo $ac_n "checking "$xe_msg_checking"""... $ac_c" 1>&6 -echo "configure:6316: checking "$xe_msg_checking"" >&5 +echo "configure:6321: checking "$xe_msg_checking"" >&5 ac_lib_var=`echo tt'_'tt_message_create | sed 'y%./+-%__p_%'` xe_check_libs=" -ltt $extra_libs" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6337: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -6385,15 +6390,15 @@ test -z "$with_cde" && { ac_safe=`echo "Dt/Dt.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for Dt/Dt.h""... $ac_c" 1>&6 -echo "configure:6389: checking for Dt/Dt.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:6397: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:6402: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -6416,12 +6421,12 @@ } test -z "$with_cde" && { echo $ac_n "checking for DtDndDragStart in -lDtSvc""... $ac_c" 1>&6 -echo "configure:6420: checking for DtDndDragStart in -lDtSvc" >&5 +echo "configure:6425: checking for DtDndDragStart in -lDtSvc" >&5 ac_lib_var=`echo DtSvc'_'DtDndDragStart | sed 'y%./+-%__p_%'` xe_check_libs=" -lDtSvc " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6441: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -6501,7 +6506,7 @@ fi echo $ac_n "checking if drag and drop API is needed""... $ac_c" 1>&6 -echo "configure:6505: checking if drag and drop API is needed" >&5 +echo "configure:6510: checking if drag and drop API is needed" >&5 if test "$with_dragndrop" != "no" ; then if test -n "$dragndrop_proto" ; then with_dragndrop=yes @@ -6522,18 +6527,18 @@ fi echo "checking for LDAP" 1>&6 -echo "configure:6526: checking for LDAP" >&5 +echo "configure:6531: checking for LDAP" >&5 test -z "$with_ldap" && { ac_safe=`echo "ldap.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for ldap.h""... $ac_c" 1>&6 -echo "configure:6529: checking for ldap.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:6537: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:6542: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -6556,15 +6561,15 @@ } test -z "$with_ldap" && { ac_safe=`echo "lber.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for lber.h""... $ac_c" 1>&6 -echo "configure:6560: checking for lber.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:6568: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:6573: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -6588,12 +6593,12 @@ if test "$with_ldap" != "no"; then echo $ac_n "checking for ldap_search in -lldap""... $ac_c" 1>&6 -echo "configure:6592: checking for ldap_search in -lldap" >&5 +echo "configure:6597: checking for ldap_search in -lldap" >&5 ac_lib_var=`echo ldap'_'ldap_search | sed 'y%./+-%__p_%'` xe_check_libs=" -lldap " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6613: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -6629,12 +6634,12 @@ xe_msg_checking="for ldap_open in -lldap" test -n "-llber" && xe_msg_checking="$xe_msg_checking using extra libs -llber" echo $ac_n "checking "$xe_msg_checking"""... $ac_c" 1>&6 -echo "configure:6633: checking "$xe_msg_checking"" >&5 +echo "configure:6638: checking "$xe_msg_checking"" >&5 ac_lib_var=`echo ldap'_'ldap_open | sed 'y%./+-%__p_%'` xe_check_libs=" -lldap -llber" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6654: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -6670,12 +6675,12 @@ xe_msg_checking="for ldap_open in -lldap" test -n "-llber -lkrb" && xe_msg_checking="$xe_msg_checking using extra libs -llber -lkrb" echo $ac_n "checking "$xe_msg_checking"""... $ac_c" 1>&6 -echo "configure:6674: checking "$xe_msg_checking"" >&5 +echo "configure:6679: checking "$xe_msg_checking"" >&5 ac_lib_var=`echo ldap'_'ldap_open | sed 'y%./+-%__p_%'` xe_check_libs=" -lldap -llber -lkrb" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6695: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -6711,12 +6716,12 @@ xe_msg_checking="for ldap_open in -lldap" test -n "-llber -lkrb -ldes" && xe_msg_checking="$xe_msg_checking using extra libs -llber -lkrb -ldes" echo $ac_n "checking "$xe_msg_checking"""... $ac_c" 1>&6 -echo "configure:6715: checking "$xe_msg_checking"" >&5 +echo "configure:6720: checking "$xe_msg_checking"" >&5 ac_lib_var=`echo ldap'_'ldap_open | sed 'y%./+-%__p_%'` xe_check_libs=" -lldap -llber -lkrb -ldes" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6736: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -6778,10 +6783,10 @@ for ac_func in ldap_set_option ldap_get_lderrno ldap_result2error ldap_parse_result do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:6782: checking for $ac_func" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6813: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -6836,15 +6841,15 @@ if test "$window_system" != "none"; then echo "checking for graphics libraries" 1>&6 -echo "configure:6840: checking for graphics libraries" >&5 +echo "configure:6845: checking for graphics libraries" >&5 xpm_problem="" if test -z "$with_xpm"; then echo $ac_n "checking for Xpm - no older than 3.4f""... $ac_c" 1>&6 -echo "configure:6845: checking for Xpm - no older than 3.4f" >&5 +echo "configure:6850: checking for Xpm - no older than 3.4f" >&5 xe_check_libs=-lXpm cat > conftest.$ac_ext < int main(int c, char **v) { @@ -6852,7 +6857,7 @@ XpmIncludeVersion != XpmLibraryVersion() ? 1 : XpmIncludeVersion < 30406 ? 2 : 0 ;} EOF -if { (eval echo configure:6856: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:6861: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ./conftest dummy_arg; xpm_status=$?; if test "$xpm_status" = "0"; then @@ -6894,17 +6899,17 @@ libs_x="-lXpm $libs_x" && if test "$extra_verbose" = "yes"; then echo " Prepending \"-lXpm\" to \$libs_x"; fi echo $ac_n "checking for \"FOR_MSW\" xpm""... $ac_c" 1>&6 -echo "configure:6898: checking for \"FOR_MSW\" xpm" >&5 +echo "configure:6903: checking for \"FOR_MSW\" xpm" >&5 xe_check_libs=-lXpm cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6913: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* xpm_for_msw=no else @@ -6930,15 +6935,15 @@ test -z "$with_xface" && { ac_safe=`echo "compface.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for compface.h""... $ac_c" 1>&6 -echo "configure:6934: checking for compface.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:6942: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:6947: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -6961,12 +6966,12 @@ } test -z "$with_xface" && { echo $ac_n "checking for UnGenFace in -lcompface""... $ac_c" 1>&6 -echo "configure:6965: checking for UnGenFace in -lcompface" >&5 +echo "configure:6970: checking for UnGenFace in -lcompface" >&5 ac_lib_var=`echo compface'_'UnGenFace | sed 'y%./+-%__p_%'` xe_check_libs=" -lcompface " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:6986: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7029,12 +7034,12 @@ if test "$with_png $with_tiff" != "no no"; then echo $ac_n "checking for inflate in -lc""... $ac_c" 1>&6 -echo "configure:7033: checking for inflate in -lc" >&5 +echo "configure:7038: checking for inflate in -lc" >&5 ac_lib_var=`echo c'_'inflate | sed 'y%./+-%__p_%'` xe_check_libs=" -lc " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7054: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7064,12 +7069,12 @@ echo "$ac_t""no" 1>&6 echo $ac_n "checking for inflate in -lz""... $ac_c" 1>&6 -echo "configure:7068: checking for inflate in -lz" >&5 +echo "configure:7073: checking for inflate in -lz" >&5 ac_lib_var=`echo z'_'inflate | sed 'y%./+-%__p_%'` xe_check_libs=" -lz " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7089: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7099,12 +7104,12 @@ echo "$ac_t""no" 1>&6 echo $ac_n "checking for inflate in -lgz""... $ac_c" 1>&6 -echo "configure:7103: checking for inflate in -lgz" >&5 +echo "configure:7108: checking for inflate in -lgz" >&5 ac_lib_var=`echo gz'_'inflate | sed 'y%./+-%__p_%'` xe_check_libs=" -lgz " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7124: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7145,15 +7150,15 @@ test -z "$with_jpeg" && { ac_safe=`echo "jpeglib.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for jpeglib.h""... $ac_c" 1>&6 -echo "configure:7149: checking for jpeglib.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:7157: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:7162: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -7176,12 +7181,12 @@ } test -z "$with_jpeg" && { echo $ac_n "checking for jpeg_destroy_decompress in -ljpeg""... $ac_c" 1>&6 -echo "configure:7180: checking for jpeg_destroy_decompress in -ljpeg" >&5 +echo "configure:7185: checking for jpeg_destroy_decompress in -ljpeg" >&5 ac_lib_var=`echo jpeg'_'jpeg_destroy_decompress | sed 'y%./+-%__p_%'` xe_check_libs=" -ljpeg " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7201: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7228,10 +7233,10 @@ png_problem="" test -z "$with_png" && { echo $ac_n "checking for pow""... $ac_c" 1>&6 -echo "configure:7232: checking for pow" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7263: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_pow=yes" else @@ -7275,15 +7280,15 @@ } test -z "$with_png" && { ac_safe=`echo "png.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for png.h""... $ac_c" 1>&6 -echo "configure:7279: checking for png.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:7287: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:7292: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -7306,12 +7311,12 @@ } test -z "$with_png" && { echo $ac_n "checking for png_read_image in -lpng""... $ac_c" 1>&6 -echo "configure:7310: checking for png_read_image in -lpng" >&5 +echo "configure:7315: checking for png_read_image in -lpng" >&5 ac_lib_var=`echo png'_'png_read_image | sed 'y%./+-%__p_%'` xe_check_libs=" -lpng " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7331: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7345,10 +7350,10 @@ } if test -z "$with_png"; then echo $ac_n "checking for workable png version information""... $ac_c" 1>&6 -echo "configure:7349: checking for workable png version information" >&5 +echo "configure:7354: checking for workable png version information" >&5 xe_check_libs="-lpng -lz" cat > conftest.$ac_ext < int main(int c, char **v) { @@ -7356,7 +7361,7 @@ if (strcmp(png_libpng_ver, PNG_LIBPNG_VER_STRING) != 0) return 1; return (PNG_LIBPNG_VER < 10002) ? 2 : 0 ;} EOF -if { (eval echo configure:7360: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:7365: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ./conftest dummy_arg; png_status=$?; if test "$png_status" = "0"; then @@ -7399,15 +7404,15 @@ test -z "$with_tiff" && { ac_safe=`echo "tiffio.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for tiffio.h""... $ac_c" 1>&6 -echo "configure:7403: checking for tiffio.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:7411: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:7416: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -7430,12 +7435,12 @@ } test -z "$with_tiff" && { echo $ac_n "checking for TIFFClientOpen in -ltiff""... $ac_c" 1>&6 -echo "configure:7434: checking for TIFFClientOpen in -ltiff" >&5 +echo "configure:7439: checking for TIFFClientOpen in -ltiff" >&5 ac_lib_var=`echo tiff'_'TIFFClientOpen | sed 'y%./+-%__p_%'` xe_check_libs=" -ltiff " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7455: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7485,16 +7490,16 @@ if test "$with_x11" = "yes"; then echo "checking for X11 graphics libraries" 1>&6 -echo "configure:7489: checking for X11 graphics libraries" >&5 +echo "configure:7494: checking for X11 graphics libraries" >&5 echo $ac_n "checking for XawScrollbarSetThumb in -lXaw""... $ac_c" 1>&6 -echo "configure:7493: checking for XawScrollbarSetThumb in -lXaw" >&5 +echo "configure:7498: checking for XawScrollbarSetThumb in -lXaw" >&5 ac_lib_var=`echo Xaw'_'XawScrollbarSetThumb | sed 'y%./+-%__p_%'` xe_check_libs=" -lXaw " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7514: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7527,17 +7532,57 @@ + +echo $ac_n "checking for XawScrollbarSetThumb in -lXaw3d""... $ac_c" 1>&6 +echo "configure:7538: checking for XawScrollbarSetThumb in -lXaw3d" >&5 +ac_lib_var=`echo Xaw3d'_'XawScrollbarSetThumb | sed 'y%./+-%__p_%'` + +xe_check_libs=" -lXaw3d " +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +xe_check_libs="" + +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes" ; then + echo "$ac_t""yes" 1>&6 + have_xaw3d=yes +else + echo "$ac_t""no" 1>&6 +have_xaw3d=no +fi + + + ac_safe=`echo "Xm/Xm.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for Xm/Xm.h""... $ac_c" 1>&6 -echo "configure:7533: checking for Xm/Xm.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:7541: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:7586: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -7554,12 +7599,12 @@ echo "$ac_t""yes" 1>&6 echo $ac_n "checking for XmStringFree in -lXm""... $ac_c" 1>&6 -echo "configure:7558: checking for XmStringFree in -lXm" >&5 +echo "configure:7603: checking for XmStringFree in -lXm" >&5 ac_lib_var=`echo Xm'_'XmStringFree | sed 'y%./+-%__p_%'` xe_check_libs=" -lXm " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:7619: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7599,9 +7644,9 @@ if test "$have_motif" = "yes"; then echo $ac_n "checking for Lesstif""... $ac_c" 1>&6 -echo "configure:7603: checking for Lesstif" >&5 +echo "configure:7648: checking for Lesstif" >&5 cat > conftest.$ac_ext < #ifdef LESSTIF_VERSION @@ -7629,6 +7674,7 @@ esac case "$with_dialogs" in "" | "yes" | "lucid" ) if test "$have_motif" = "yes"; then with_dialogs="motif" + elif test "$have_xaw3d" = "yes"; then with_dialogs="athena3d" elif test "$have_xaw" = "yes"; then with_dialogs="athena" else with_dialogs=no fi ;; @@ -7636,15 +7682,41 @@ case "$with_scrollbars" in "" | "yes" ) with_scrollbars="lucid" ;; esac -case "$with_widgets" in "" | "yes" ) +case "$with_widgets" in "" | "yes" | "lucid") if test "$have_motif" = "yes"; then with_widgets="motif" + elif test "$have_xaw3d" = "yes"; then with_widgets="athena3d" + elif test "$have_xaw" = "yes"; then with_widgets="athena" else with_widgets=no fi ;; esac all_widgets="$with_menubars $with_scrollbars $with_dialogs $with_toolbars $with_widgets" -case "$all_widgets" in *athena* ) +case "$all_widgets" in + *athena*3d ) + { test "$extra_verbose" = "yes" && cat << \EOF + Defining LWLIB_USES_ATHENA +EOF +cat >> confdefs.h <<\EOF +#define LWLIB_USES_ATHENA 1 +EOF +} + + { test "$extra_verbose" = "yes" && cat << \EOF + Defining NEED_ATHENA +EOF +cat >> confdefs.h <<\EOF +#define NEED_ATHENA 1 +EOF +} + + lwlib_objs="$lwlib_objs lwlib-Xaw.o" && if test "$extra_verbose" = "yes"; then echo " Appending \"lwlib-Xaw.o\" to \$lwlib_objs"; fi + if test "$have_xaw3d"; then + libs_x="-lXaw3d $libs_x" && if test "$extra_verbose" = "yes"; then echo " Prepending \"-lXaw3d\" to \$libs_x"; fi + else + libs_x="-lXaw $libs_x" && if test "$extra_verbose" = "yes"; then echo " Prepending \"-lXaw\" to \$libs_x"; fi + fi ;; + *athena* ) { test "$extra_verbose" = "yes" && cat << \EOF Defining LWLIB_USES_ATHENA EOF @@ -7689,6 +7761,11 @@ test "$with_menubars" = "lucid" && lwlib_objs="$lwlib_objs xlwmenu.o" && if test "$extra_verbose" = "yes"; then echo " Appending \"xlwmenu.o\" to \$lwlib_objs"; fi test "$with_menubars" = "motif" && lwlib_objs="$lwlib_objs xlwmenu.o" && if test "$extra_verbose" = "yes"; then echo " Appending \"xlwmenu.o\" to \$lwlib_objs"; fi test "$with_scrollbars" = "lucid" && lwlib_objs="$lwlib_objs xlwscrollbar.o" && if test "$extra_verbose" = "yes"; then echo " Appending \"xlwscrollbar.o\" to \$lwlib_objs"; fi +test "$with_widgets" != "no" && test "$with_widgets" != "msw" && \ + lwlib_objs="$lwlib_objs xlwtabs.o xlwgcs.o" && if test "$extra_verbose" = "yes"; then echo " Appending \"xlwtabs.o xlwgcs.o\" to \$lwlib_objs"; fi +case "$with_widgets" in athena* ) + lwlib_objs="$lwlib_objs xlwradio.o xlwcheckbox.o xlwgauge.o" && if test "$extra_verbose" = "yes"; then echo " Appending \"xlwradio.o xlwcheckbox.o xlwgauge.o\" to \$lwlib_objs"; fi;; +esac case "$all_widgets" in *lucid* ) { test "$extra_verbose" = "yes" && cat << \EOF Defining NEED_LUCID @@ -7735,6 +7812,23 @@ EOF } +case "$with_widgets" in athena* ) { test "$extra_verbose" = "yes" && cat << \EOF + Defining LWLIB_WIDGETS_ATHENA +EOF +cat >> confdefs.h <<\EOF +#define LWLIB_WIDGETS_ATHENA 1 +EOF +} +;; esac +test "$with_widgets" != "no" && test "$with_widgets" != "msw" && \ + { test "$extra_verbose" = "yes" && cat << \EOF + Defining LWLIB_TABS_LUCID +EOF +cat >> confdefs.h <<\EOF +#define LWLIB_TABS_LUCID 1 +EOF +} + test "$with_menubars" != "no" && { test "$extra_verbose" = "yes" && cat << \EOF Defining HAVE_MENUBARS @@ -7768,6 +7862,14 @@ EOF } +test "$with_widgets" != "no" && { test "$extra_verbose" = "yes" && cat << \EOF + Defining HAVE_WIDGETS +EOF +cat >> confdefs.h <<\EOF +#define HAVE_WIDGETS 1 +EOF +} + test "$with_menubars" = "lucid" && { test "$extra_verbose" = "yes" && cat << \EOF Defining LWLIB_MENUBARS_LUCID @@ -7810,6 +7912,14 @@ EOF } +test "$with_widgets" = "motif" && { test "$extra_verbose" = "yes" && cat << \EOF + Defining LWLIB_WIDGETS_MOTIF +EOF +cat >> confdefs.h <<\EOF +#define LWLIB_WIDGETS_MOTIF 1 +EOF +} + test "$with_menubars" != "no" && extra_objs="$extra_objs menubar.o" && if test "$extra_verbose" = "yes"; then echo " xemacs will be linked with \"menubar.o\"" @@ -7869,7 +7979,7 @@ if test "$with_mule" = "yes" ; then echo "checking for Mule-related features" 1>&6 -echo "configure:7873: checking for Mule-related features" >&5 +echo "configure:7983: checking for Mule-related features" >&5 { test "$extra_verbose" = "yes" && cat << \EOF Defining MULE EOF @@ -7894,15 +8004,15 @@ do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:7898: checking for $ac_hdr" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:7906: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:8016: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -7933,12 +8043,12 @@ echo $ac_n "checking for strerror in -lintl""... $ac_c" 1>&6 -echo "configure:7937: checking for strerror in -lintl" >&5 +echo "configure:8047: checking for strerror in -lintl" >&5 ac_lib_var=`echo intl'_'strerror | sed 'y%./+-%__p_%'` xe_check_libs=" -lintl " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8063: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -7982,18 +8092,18 @@ echo "checking for Mule input methods" 1>&6 -echo "configure:7986: checking for Mule input methods" >&5 +echo "configure:8096: checking for Mule input methods" >&5 case "$with_xim" in "" | "yes" ) echo "checking for XIM" 1>&6 -echo "configure:7989: checking for XIM" >&5 +echo "configure:8099: checking for XIM" >&5 echo $ac_n "checking for XOpenIM in -lX11""... $ac_c" 1>&6 -echo "configure:7992: checking for XOpenIM in -lX11" >&5 +echo "configure:8102: checking for XOpenIM in -lX11" >&5 ac_lib_var=`echo X11'_'XOpenIM | sed 'y%./+-%__p_%'` xe_check_libs=" -lX11 " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8118: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8028,12 +8138,12 @@ if test "$have_motif $have_lesstif" = "yes no"; then echo $ac_n "checking for XmImMbLookupString in -lXm""... $ac_c" 1>&6 -echo "configure:8032: checking for XmImMbLookupString in -lXm" >&5 +echo "configure:8142: checking for XmImMbLookupString in -lXm" >&5 ac_lib_var=`echo Xm'_'XmImMbLookupString | sed 'y%./+-%__p_%'` xe_check_libs=" -lXm " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8158: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8109,15 +8219,15 @@ if test "$with_xfs" = "yes" ; then echo "checking for XFontSet" 1>&6 -echo "configure:8113: checking for XFontSet" >&5 +echo "configure:8223: checking for XFontSet" >&5 echo $ac_n "checking for XmbDrawString in -lX11""... $ac_c" 1>&6 -echo "configure:8116: checking for XmbDrawString in -lX11" >&5 +echo "configure:8226: checking for XmbDrawString in -lX11" >&5 ac_lib_var=`echo X11'_'XmbDrawString | sed 'y%./+-%__p_%'` xe_check_libs=" -lX11 " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8242: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8168,15 +8278,15 @@ test "$with_wnn6" = "yes" && with_wnn=yes # wnn6 implies wnn support test -z "$with_wnn" && { ac_safe=`echo "wnn/jllib.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for wnn/jllib.h""... $ac_c" 1>&6 -echo "configure:8172: checking for wnn/jllib.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:8180: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:8290: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -8201,10 +8311,10 @@ for ac_func in crypt do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:8205: checking for $ac_func" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8341: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -8256,12 +8366,12 @@ test "$ac_cv_func_crypt" != "yes" && { echo $ac_n "checking for crypt in -lcrypt""... $ac_c" 1>&6 -echo "configure:8260: checking for crypt in -lcrypt" >&5 +echo "configure:8370: checking for crypt in -lcrypt" >&5 ac_lib_var=`echo crypt'_'crypt | sed 'y%./+-%__p_%'` xe_check_libs=" -lcrypt " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8386: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8307,12 +8417,12 @@ if test -z "$with_wnn" -o "$with_wnn" = "yes"; then echo $ac_n "checking for jl_dic_list_e in -lwnn""... $ac_c" 1>&6 -echo "configure:8311: checking for jl_dic_list_e in -lwnn" >&5 +echo "configure:8421: checking for jl_dic_list_e in -lwnn" >&5 ac_lib_var=`echo wnn'_'jl_dic_list_e | sed 'y%./+-%__p_%'` xe_check_libs=" -lwnn " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8437: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8341,12 +8451,12 @@ else echo "$ac_t""no" 1>&6 echo $ac_n "checking for jl_dic_list_e in -lwnn4""... $ac_c" 1>&6 -echo "configure:8345: checking for jl_dic_list_e in -lwnn4" >&5 +echo "configure:8455: checking for jl_dic_list_e in -lwnn4" >&5 ac_lib_var=`echo wnn4'_'jl_dic_list_e | sed 'y%./+-%__p_%'` xe_check_libs=" -lwnn4 " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8471: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8375,12 +8485,12 @@ else echo "$ac_t""no" 1>&6 echo $ac_n "checking for jl_dic_list_e in -lwnn6""... $ac_c" 1>&6 -echo "configure:8379: checking for jl_dic_list_e in -lwnn6" >&5 +echo "configure:8489: checking for jl_dic_list_e in -lwnn6" >&5 ac_lib_var=`echo wnn6'_'jl_dic_list_e | sed 'y%./+-%__p_%'` xe_check_libs=" -lwnn6 " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8505: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8409,12 +8519,12 @@ else echo "$ac_t""no" 1>&6 echo $ac_n "checking for dic_list_e in -lwnn6_fromsrc""... $ac_c" 1>&6 -echo "configure:8413: checking for dic_list_e in -lwnn6_fromsrc" >&5 +echo "configure:8523: checking for dic_list_e in -lwnn6_fromsrc" >&5 ac_lib_var=`echo wnn6_fromsrc'_'dic_list_e | sed 'y%./+-%__p_%'` xe_check_libs=" -lwnn6_fromsrc " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8539: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8473,12 +8583,12 @@ if test "$with_wnn6" != "no"; then echo $ac_n "checking for jl_fi_dic_list in -l$libwnn""... $ac_c" 1>&6 -echo "configure:8477: checking for jl_fi_dic_list in -l$libwnn" >&5 +echo "configure:8587: checking for jl_fi_dic_list in -l$libwnn" >&5 ac_lib_var=`echo $libwnn'_'jl_fi_dic_list | sed 'y%./+-%__p_%'` xe_check_libs=" -l$libwnn " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8603: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8524,15 +8634,15 @@ if test "$with_canna" != "no"; then ac_safe=`echo "canna/jrkanji.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for canna/jrkanji.h""... $ac_c" 1>&6 -echo "configure:8528: checking for canna/jrkanji.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:8536: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:8646: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -8559,15 +8669,15 @@ c_switch_site="$c_switch_site -I/usr/local/canna/include" ac_safe=`echo "canna/jrkanji.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for canna/jrkanji.h""... $ac_c" 1>&6 -echo "configure:8563: checking for canna/jrkanji.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:8571: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:8681: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -8595,15 +8705,15 @@ test -z "$with_canna" && { ac_safe=`echo "canna/RK.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for canna/RK.h""... $ac_c" 1>&6 -echo "configure:8599: checking for canna/RK.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:8607: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:8717: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -8626,12 +8736,12 @@ } test -z "$with_canna" && { echo $ac_n "checking for RkBgnBun in -lRKC""... $ac_c" 1>&6 -echo "configure:8630: checking for RkBgnBun in -lRKC" >&5 +echo "configure:8740: checking for RkBgnBun in -lRKC" >&5 ac_lib_var=`echo RKC'_'RkBgnBun | sed 'y%./+-%__p_%'` xe_check_libs=" -lRKC " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8756: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8665,12 +8775,12 @@ } test -z "$with_canna" && { echo $ac_n "checking for jrKanjiControl in -lcanna""... $ac_c" 1>&6 -echo "configure:8669: checking for jrKanjiControl in -lcanna" >&5 +echo "configure:8779: checking for jrKanjiControl in -lcanna" >&5 ac_lib_var=`echo canna'_'jrKanjiControl | sed 'y%./+-%__p_%'` xe_check_libs=" -lcanna " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8795: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8730,12 +8840,12 @@ libs_x="-lXm $libs_x" && if test "$extra_verbose" = "yes"; then echo " Prepending \"-lXm\" to \$libs_x"; fi echo $ac_n "checking for layout_object_getvalue in -li18n""... $ac_c" 1>&6 -echo "configure:8734: checking for layout_object_getvalue in -li18n" >&5 +echo "configure:8844: checking for layout_object_getvalue in -li18n" >&5 ac_lib_var=`echo i18n'_'layout_object_getvalue | sed 'y%./+-%__p_%'` xe_check_libs=" -li18n " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8860: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -8829,13 +8939,13 @@ fi -for ac_func in cbrt closedir dup2 eaccess fmod fpathconf frexp ftime gethostname getpagesize gettimeofday getcwd getwd logb lrand48 matherr mkdir mktime perror poll random rename res_init rint rmdir select setitimer setpgid setlocale setsid sigblock sighold sigprocmask snprintf strcasecmp strerror tzset ulimit usleep utimes waitpid vsnprintf +for ac_func in cbrt closedir dup2 eaccess fmod fpathconf frexp ftime gethostname getpagesize gettimeofday getcwd getpt getwd logb lrand48 matherr mkdir mktime perror poll random rename res_init rint rmdir select setitimer setpgid setlocale setsid sigblock sighold sigprocmask snprintf stpcpy strcasecmp strerror tzset ulimit usleep utimes waitpid vsnprintf do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:8836: checking for $ac_func" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:8972: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -8899,10 +9009,10 @@ * ) for ac_func in realpath do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:8903: checking for $ac_func" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9039: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -8961,10 +9071,10 @@ for ac_func in getloadavg do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:8965: checking for $ac_func" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9101: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -9023,12 +9133,12 @@ echo $ac_n "checking for kstat_open in -lkstat""... $ac_c" 1>&6 -echo "configure:9027: checking for kstat_open in -lkstat" >&5 +echo "configure:9137: checking for kstat_open in -lkstat" >&5 ac_lib_var=`echo kstat'_'kstat_open | sed 'y%./+-%__p_%'` xe_check_libs=" -lkstat " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9153: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -9073,12 +9183,12 @@ echo $ac_n "checking for kvm_read in -lkvm""... $ac_c" 1>&6 -echo "configure:9077: checking for kvm_read in -lkvm" >&5 +echo "configure:9187: checking for kvm_read in -lkvm" >&5 ac_lib_var=`echo kvm'_'kvm_read | sed 'y%./+-%__p_%'` xe_check_libs=" -lkvm " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9203: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -9123,16 +9233,16 @@ fi echo $ac_n "checking whether netdb declares h_errno""... $ac_c" 1>&6 -echo "configure:9127: checking whether netdb declares h_errno" >&5 -cat > conftest.$ac_ext <&5 +cat > conftest.$ac_ext < int main() { return h_errno; ; return 0; } EOF -if { (eval echo configure:9136: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9246: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* echo "$ac_t""yes" 1>&6 { test "$extra_verbose" = "yes" && cat << \EOF @@ -9152,16 +9262,16 @@ rm -f conftest* echo $ac_n "checking for sigsetjmp""... $ac_c" 1>&6 -echo "configure:9156: checking for sigsetjmp" >&5 -cat > conftest.$ac_ext <&5 +cat > conftest.$ac_ext < int main() { sigjmp_buf bar; sigsetjmp (bar, 0); ; return 0; } EOF -if { (eval echo configure:9165: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:9275: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* echo "$ac_t""yes" 1>&6 { test "$extra_verbose" = "yes" && cat << \EOF @@ -9181,11 +9291,11 @@ rm -f conftest* echo $ac_n "checking whether localtime caches TZ""... $ac_c" 1>&6 -echo "configure:9185: checking whether localtime caches TZ" >&5 +echo "configure:9295: checking whether localtime caches TZ" >&5 if test "$ac_cv_func_tzset" = "yes"; then cat > conftest.$ac_ext < #if STDC_HEADERS @@ -9220,7 +9330,7 @@ exit (0); } EOF -if { (eval echo configure:9224: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:9334: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then emacs_cv_localtime_cache=no else @@ -9250,9 +9360,9 @@ if test "$HAVE_TIMEVAL" = "yes"; then echo $ac_n "checking whether gettimeofday accepts one or two arguments""... $ac_c" 1>&6 -echo "configure:9254: checking whether gettimeofday accepts one or two arguments" >&5 -cat > conftest.$ac_ext <&5 +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9388: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* echo "$ac_t""two" 1>&6 else @@ -9296,19 +9406,19 @@ echo $ac_n "checking for inline""... $ac_c" 1>&6 -echo "configure:9300: checking for inline" >&5 +echo "configure:9410: checking for inline" >&5 ac_cv_c_inline=no for ac_kw in inline __inline__ __inline; do cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:9422: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_inline=$ac_kw; break else @@ -9358,17 +9468,17 @@ # The Ultrix 4.2 mips builtin alloca declared by alloca.h only works # for constant arguments. Useless! echo $ac_n "checking for working alloca.h""... $ac_c" 1>&6 -echo "configure:9362: checking for working alloca.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < int main() { char *p = alloca(2 * sizeof(int)); ; return 0; } EOF -if { (eval echo configure:9372: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9482: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_header_alloca_h=yes else @@ -9392,10 +9502,10 @@ fi echo $ac_n "checking for alloca""... $ac_c" 1>&6 -echo "configure:9396: checking for alloca" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9537: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_func_alloca_works=yes else @@ -9462,10 +9572,10 @@ echo $ac_n "checking whether alloca needs Cray hooks""... $ac_c" 1>&6 -echo "configure:9466: checking whether alloca needs Cray hooks" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&6 -echo "configure:9493: checking for $ac_func" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9629: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -9545,10 +9655,10 @@ fi echo $ac_n "checking stack direction for C alloca""... $ac_c" 1>&6 -echo "configure:9549: checking stack direction for C alloca" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:9681: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_c_stack_direction=1 else @@ -9596,15 +9706,15 @@ ac_safe=`echo "vfork.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for vfork.h""... $ac_c" 1>&6 -echo "configure:9600: checking for vfork.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:9608: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:9718: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -9632,10 +9742,10 @@ fi echo $ac_n "checking for working vfork""... $ac_c" 1>&6 -echo "configure:9636: checking for working vfork" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < @@ -9730,7 +9840,7 @@ } } EOF -if { (eval echo configure:9734: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:9844: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_func_vfork_works=yes else @@ -9756,10 +9866,10 @@ echo $ac_n "checking for working strcoll""... $ac_c" 1>&6 -echo "configure:9760: checking for working strcoll" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < main () @@ -9769,7 +9879,7 @@ strcoll ("123", "456") >= 0); } EOF -if { (eval echo configure:9773: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:9883: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_func_strcoll_works=yes else @@ -9797,10 +9907,10 @@ for ac_func in getpgrp do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:9801: checking for $ac_func" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:9937: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -9851,10 +9961,10 @@ done echo $ac_n "checking whether getpgrp takes no argument""... $ac_c" 1>&6 -echo "configure:9855: checking whether getpgrp takes no argument" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:10023: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then ac_cv_func_getpgrp_void=yes else @@ -9936,10 +10046,10 @@ echo $ac_n "checking for working mmap""... $ac_c" 1>&6 -echo "configure:9940: checking for working mmap" >&5 +echo "configure:10050: checking for working mmap" >&5 case "$opsys" in ultrix* ) have_mmap=no ;; *) cat > conftest.$ac_ext < #include @@ -9972,7 +10082,7 @@ return 1; } EOF -if { (eval echo configure:9976: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:10086: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then have_mmap=yes else @@ -10007,15 +10117,15 @@ ac_safe=`echo "termios.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for termios.h""... $ac_c" 1>&6 -echo "configure:10011: checking for termios.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10019: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10129: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10058,15 +10168,15 @@ echo "$ac_t""no" 1>&6 ac_safe=`echo "termio.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for termio.h""... $ac_c" 1>&6 -echo "configure:10062: checking for termio.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10070: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10180: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10098,10 +10208,10 @@ echo $ac_n "checking for socket""... $ac_c" 1>&6 -echo "configure:10102: checking for socket" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:10238: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_socket=yes" else @@ -10139,15 +10249,15 @@ echo "$ac_t""yes" 1>&6 ac_safe=`echo "netinet/in.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for netinet/in.h""... $ac_c" 1>&6 -echo "configure:10143: checking for netinet/in.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10151: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10261: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10164,15 +10274,15 @@ echo "$ac_t""yes" 1>&6 ac_safe=`echo "arpa/inet.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for arpa/inet.h""... $ac_c" 1>&6 -echo "configure:10168: checking for arpa/inet.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10176: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10286: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10197,9 +10307,9 @@ } echo $ac_n "checking "for sun_len member in struct sockaddr_un"""... $ac_c" 1>&6 -echo "configure:10201: checking "for sun_len member in struct sockaddr_un"" >&5 +echo "configure:10311: checking "for sun_len member in struct sockaddr_un"" >&5 cat > conftest.$ac_ext < @@ -10210,7 +10320,7 @@ static struct sockaddr_un x; x.sun_len = 1; ; return 0; } EOF -if { (eval echo configure:10214: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:10324: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* echo "$ac_t""yes" 1>&6; { test "$extra_verbose" = "yes" && cat << \EOF Defining HAVE_SOCKADDR_SUN_LEN @@ -10228,9 +10338,9 @@ fi rm -f conftest* echo $ac_n "checking "for ip_mreq struct in netinet/in.h"""... $ac_c" 1>&6 -echo "configure:10232: checking "for ip_mreq struct in netinet/in.h"" >&5 +echo "configure:10342: checking "for ip_mreq struct in netinet/in.h"" >&5 cat > conftest.$ac_ext < @@ -10240,7 +10350,7 @@ static struct ip_mreq x; ; return 0; } EOF -if { (eval echo configure:10244: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:10354: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* echo "$ac_t""yes" 1>&6; { test "$extra_verbose" = "yes" && cat << \EOF Defining HAVE_MULTICAST @@ -10271,10 +10381,10 @@ echo $ac_n "checking for msgget""... $ac_c" 1>&6 -echo "configure:10275: checking for msgget" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:10411: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_msgget=yes" else @@ -10312,15 +10422,15 @@ echo "$ac_t""yes" 1>&6 ac_safe=`echo "sys/ipc.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for sys/ipc.h""... $ac_c" 1>&6 -echo "configure:10316: checking for sys/ipc.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10324: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10434: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10337,15 +10447,15 @@ echo "$ac_t""yes" 1>&6 ac_safe=`echo "sys/msg.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for sys/msg.h""... $ac_c" 1>&6 -echo "configure:10341: checking for sys/msg.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10349: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10459: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10383,15 +10493,15 @@ ac_safe=`echo "dirent.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for dirent.h""... $ac_c" 1>&6 -echo "configure:10387: checking for dirent.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10395: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10505: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10418,15 +10528,15 @@ echo "$ac_t""no" 1>&6 ac_safe=`echo "sys/dir.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for sys/dir.h""... $ac_c" 1>&6 -echo "configure:10422: checking for sys/dir.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10430: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10540: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10459,15 +10569,15 @@ ac_safe=`echo "nlist.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for nlist.h""... $ac_c" 1>&6 -echo "configure:10463: checking for nlist.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10471: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10581: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10497,7 +10607,7 @@ echo "checking "for sound support"" 1>&6 -echo "configure:10501: checking "for sound support"" >&5 +echo "configure:10611: checking "for sound support"" >&5 case "$with_sound" in native | both ) with_native_sound=yes;; nas | no ) with_native_sound=no;; @@ -10508,15 +10618,15 @@ if test -n "$native_sound_lib"; then ac_safe=`echo "multimedia/audio_device.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for multimedia/audio_device.h""... $ac_c" 1>&6 -echo "configure:10512: checking for multimedia/audio_device.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10520: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10630: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10564,12 +10674,12 @@ if test -z "$native_sound_lib"; then echo $ac_n "checking for ALopenport in -laudio""... $ac_c" 1>&6 -echo "configure:10568: checking for ALopenport in -laudio" >&5 +echo "configure:10678: checking for ALopenport in -laudio" >&5 ac_lib_var=`echo audio'_'ALopenport | sed 'y%./+-%__p_%'` xe_check_libs=" -laudio " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:10694: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -10611,12 +10721,12 @@ if test -z "$native_sound_lib"; then echo $ac_n "checking for AOpenAudio in -lAlib""... $ac_c" 1>&6 -echo "configure:10615: checking for AOpenAudio in -lAlib" >&5 +echo "configure:10725: checking for AOpenAudio in -lAlib" >&5 ac_lib_var=`echo Alib'_'AOpenAudio | sed 'y%./+-%__p_%'` xe_check_libs=" -lAlib " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:10741: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -10665,15 +10775,15 @@ for dir in "machine" "sys" "linux"; do ac_safe=`echo "${dir}/soundcard.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for ${dir}/soundcard.h""... $ac_c" 1>&6 -echo "configure:10669: checking for ${dir}/soundcard.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10677: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10787: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10743,7 +10853,7 @@ fi libs_x="-laudio $libs_x" && if test "$extra_verbose" = "yes"; then echo " Prepending \"-laudio\" to \$libs_x"; fi cat > conftest.$ac_ext < EOF @@ -10770,7 +10880,7 @@ if test "$with_tty" = "yes" ; then echo "checking for TTY-related features" 1>&6 -echo "configure:10774: checking for TTY-related features" >&5 +echo "configure:10884: checking for TTY-related features" >&5 { test "$extra_verbose" = "yes" && cat << \EOF Defining HAVE_TTY EOF @@ -10786,12 +10896,12 @@ if test -z "$with_ncurses"; then echo $ac_n "checking for tgetent in -lncurses""... $ac_c" 1>&6 -echo "configure:10790: checking for tgetent in -lncurses" >&5 +echo "configure:10900: checking for tgetent in -lncurses" >&5 ac_lib_var=`echo ncurses'_'tgetent | sed 'y%./+-%__p_%'` xe_check_libs=" -lncurses " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:10916: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -10835,15 +10945,15 @@ ac_safe=`echo "ncurses/curses.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for ncurses/curses.h""... $ac_c" 1>&6 -echo "configure:10839: checking for ncurses/curses.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10847: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10957: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10865,15 +10975,15 @@ ac_safe=`echo "ncurses/term.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for ncurses/term.h""... $ac_c" 1>&6 -echo "configure:10869: checking for ncurses/term.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10877: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:10987: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10903,15 +11013,15 @@ c_switch_site="$c_switch_site -I/usr/include/ncurses" ac_safe=`echo "ncurses/curses.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for ncurses/curses.h""... $ac_c" 1>&6 -echo "configure:10907: checking for ncurses/curses.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:10915: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:11025: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -10946,12 +11056,12 @@ for lib in curses termlib termcap; do echo $ac_n "checking for tgetent in -l$lib""... $ac_c" 1>&6 -echo "configure:10950: checking for tgetent in -l$lib" >&5 +echo "configure:11060: checking for tgetent in -l$lib" >&5 ac_lib_var=`echo $lib'_'tgetent | sed 'y%./+-%__p_%'` xe_check_libs=" -l$lib " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11076: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -10993,12 +11103,12 @@ else echo $ac_n "checking for tgetent in -lcurses""... $ac_c" 1>&6 -echo "configure:10997: checking for tgetent in -lcurses" >&5 +echo "configure:11107: checking for tgetent in -lcurses" >&5 ac_lib_var=`echo curses'_'tgetent | sed 'y%./+-%__p_%'` xe_check_libs=" -lcurses " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11123: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11027,12 +11137,12 @@ else echo "$ac_t""no" 1>&6 echo $ac_n "checking for tgetent in -ltermcap""... $ac_c" 1>&6 -echo "configure:11031: checking for tgetent in -ltermcap" >&5 +echo "configure:11141: checking for tgetent in -ltermcap" >&5 ac_lib_var=`echo termcap'_'tgetent | sed 'y%./+-%__p_%'` xe_check_libs=" -ltermcap " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11157: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11091,15 +11201,15 @@ test -z "$with_gpm" && { ac_safe=`echo "gpm.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for gpm.h""... $ac_c" 1>&6 -echo "configure:11095: checking for gpm.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:11103: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:11213: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -11122,12 +11232,12 @@ } test -z "$with_gpm" && { echo $ac_n "checking for Gpm_Open in -lgpm""... $ac_c" 1>&6 -echo "configure:11126: checking for Gpm_Open in -lgpm" >&5 +echo "configure:11236: checking for Gpm_Open in -lgpm" >&5 ac_lib_var=`echo gpm'_'Gpm_Open | sed 'y%./+-%__p_%'` xe_check_libs=" -lgpm " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11252: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11188,20 +11298,20 @@ test "$with_database_gnudbm $with_database_dbm $with_database_berkdb" \ != "no no no" && echo "checking for database support" 1>&6 -echo "configure:11192: checking for database support" >&5 +echo "configure:11302: checking for database support" >&5 if test "$with_database_gnudbm $with_database_dbm" != "no no"; then ac_safe=`echo "ndbm.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for ndbm.h""... $ac_c" 1>&6 -echo "configure:11197: checking for ndbm.h" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:11205: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:11315: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -11231,12 +11341,12 @@ if test "$with_database_gnudbm" != "no"; then echo $ac_n "checking for dbm_open in -lgdbm""... $ac_c" 1>&6 -echo "configure:11235: checking for dbm_open in -lgdbm" >&5 +echo "configure:11345: checking for dbm_open in -lgdbm" >&5 ac_lib_var=`echo gdbm'_'dbm_open | sed 'y%./+-%__p_%'` xe_check_libs=" -lgdbm " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11361: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11275,10 +11385,10 @@ if test "$with_database_dbm" != "no"; then echo $ac_n "checking for dbm_open""... $ac_c" 1>&6 -echo "configure:11279: checking for dbm_open" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11415: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_dbm_open=yes" else @@ -11320,12 +11430,12 @@ echo $ac_n "checking for dbm_open in -ldbm""... $ac_c" 1>&6 -echo "configure:11324: checking for dbm_open in -ldbm" >&5 +echo "configure:11434: checking for dbm_open in -ldbm" >&5 ac_lib_var=`echo dbm'_'dbm_open | sed 'y%./+-%__p_%'` xe_check_libs=" -ldbm " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11450: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11377,10 +11487,10 @@ if test "$with_database_berkdb" != "no"; then echo $ac_n "checking for Berkeley db.h""... $ac_c" 1>&6 -echo "configure:11381: checking for Berkeley db.h" >&5 +echo "configure:11491: checking for Berkeley db.h" >&5 for path in "db/db.h" "db.h"; do cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:11512: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* db_h_path="$path"; break else @@ -11414,9 +11524,9 @@ if test "$with_database_berkdb" != "no"; then echo $ac_n "checking for Berkeley DB version""... $ac_c" 1>&6 -echo "configure:11418: checking for Berkeley DB version" >&5 +echo "configure:11528: checking for Berkeley DB version" >&5 cat > conftest.$ac_ext < #if DB_VERSION_MAJOR > 1 @@ -11435,10 +11545,10 @@ rm -f conftest* echo $ac_n "checking for $dbfunc""... $ac_c" 1>&6 -echo "configure:11439: checking for $dbfunc" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11575: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$dbfunc=yes" else @@ -11480,12 +11590,12 @@ echo $ac_n "checking for $dbfunc in -ldb""... $ac_c" 1>&6 -echo "configure:11484: checking for $dbfunc in -ldb" >&5 +echo "configure:11594: checking for $dbfunc in -ldb" >&5 ac_lib_var=`echo db'_'$dbfunc | sed 'y%./+-%__p_%'` xe_check_libs=" -ldb " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11610: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11560,12 +11670,12 @@ if test "$with_socks" = "yes"; then echo $ac_n "checking for SOCKSinit in -lsocks""... $ac_c" 1>&6 -echo "configure:11564: checking for SOCKSinit in -lsocks" >&5 +echo "configure:11674: checking for SOCKSinit in -lsocks" >&5 ac_lib_var=`echo socks'_'SOCKSinit | sed 'y%./+-%__p_%'` xe_check_libs=" -lsocks " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11690: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11633,15 +11743,15 @@ do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:11637: checking for $ac_hdr" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:11645: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:11755: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -11680,12 +11790,12 @@ test -z "$with_modules" && test ! -z "$have_dlfcn" && { echo $ac_n "checking for dlopen in -ldl""... $ac_c" 1>&6 -echo "configure:11684: checking for dlopen in -ldl" >&5 +echo "configure:11794: checking for dlopen in -ldl" >&5 ac_lib_var=`echo dl'_'dlopen | sed 'y%./+-%__p_%'` xe_check_libs=" -ldl " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11810: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11725,12 +11835,12 @@ } test -z "$with_modules" && test ! -z "$have_dlfcn" && { echo $ac_n "checking for _dlopen in -lc""... $ac_c" 1>&6 -echo "configure:11729: checking for _dlopen in -lc" >&5 +echo "configure:11839: checking for _dlopen in -lc" >&5 ac_lib_var=`echo c'_'_dlopen | sed 'y%./+-%__p_%'` xe_check_libs=" -lc " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11855: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11770,12 +11880,12 @@ } test -z "$with_modules" && test ! -z "$have_dlfcn" && { echo $ac_n "checking for dlopen in -lc""... $ac_c" 1>&6 -echo "configure:11774: checking for dlopen in -lc" >&5 +echo "configure:11884: checking for dlopen in -lc" >&5 ac_lib_var=`echo c'_'dlopen | sed 'y%./+-%__p_%'` xe_check_libs=" -lc " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11900: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11815,12 +11925,12 @@ } test -z "$with_modules" && { echo $ac_n "checking for shl_load in -ldld""... $ac_c" 1>&6 -echo "configure:11819: checking for shl_load in -ldld" >&5 +echo "configure:11929: checking for shl_load in -ldld" >&5 ac_lib_var=`echo dld'_'shl_load | sed 'y%./+-%__p_%'` xe_check_libs=" -ldld " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11945: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11860,12 +11970,12 @@ } test -z "$with_modules" && { echo $ac_n "checking for dld_init in -ldld""... $ac_c" 1>&6 -echo "configure:11864: checking for dld_init in -ldld" >&5 +echo "configure:11974: checking for dld_init in -ldld" >&5 ac_lib_var=`echo dld'_'dld_init | sed 'y%./+-%__p_%'` xe_check_libs=" -ldld " cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11990: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11915,7 +12025,7 @@ xealias=$internal_configuration echo "checking how to build dynamic libraries for ${xehost}" 1>&6 -echo "configure:11919: checking how to build dynamic libraries for ${xehost}" >&5 +echo "configure:12029: checking how to build dynamic libraries for ${xehost}" >&5 # Transform *-*-linux* to *-*-linux-gnu*, to support old configure scripts. case "$xehost" in *-*-linux-gnu*) ;; @@ -11943,9 +12053,9 @@ XEGCC=yes else echo $ac_n "checking checking whether we are using GNU C""... $ac_c" 1>&6 -echo "configure:11947: checking checking whether we are using GNU C" >&5 +echo "configure:12057: checking checking whether we are using GNU C" >&5 cat > conftest.$ac_ext <&6 -echo "configure:11971: checking how to produce PIC code" >&5 +echo "configure:12081: checking how to produce PIC code" >&5 wl= can_build_shared=yes @@ -12060,18 +12170,18 @@ # Check to make sure the dll_cflags actually works. echo $ac_n "checking if PIC flag ${dll_cflags} really works""... $ac_c" 1>&6 -echo "configure:12064: checking if PIC flag ${dll_cflags} really works" >&5 +echo "configure:12174: checking if PIC flag ${dll_cflags} really works" >&5 save_CFLAGS="$CFLAGS" CFLAGS="$CFLAGS $dll_cflags -DPIC" cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:12185: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* # On HP-UX, the stripped-down bundled CC doesn't accept +Z, but also @@ -12102,7 +12212,7 @@ xldf= xcldf= echo $ac_n "checking if C compiler can produce shared libraries""... $ac_c" 1>&6 -echo "configure:12106: checking if C compiler can produce shared libraries" >&5 +echo "configure:12216: checking if C compiler can produce shared libraries" >&5 if test "$XEGCC" = yes; then xcldf="-shared" xldf="-shared" @@ -12153,14 +12263,14 @@ xe_libs= ac_link='${CC-cc} -o conftest $CFLAGS '"$xe_cppflags $xe_ldflags"' conftest.$ac_ext '"$xe_libs"' 1>&5' cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:12274: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* cc_produces_so=yes else @@ -12185,7 +12295,7 @@ if test "$XEGCC" = yes; then # Check if gcc -print-prog-name=ld gives a path. echo $ac_n "checking for ld used by GCC""... $ac_c" 1>&6 -echo "configure:12189: checking for ld used by GCC" >&5 +echo "configure:12299: checking for ld used by GCC" >&5 ac_prog=`($CC -print-prog-name=ld) 2>&5` case "$ac_prog" in # Accept absolute paths. @@ -12210,7 +12320,7 @@ esac else echo $ac_n "checking for GNU ld""... $ac_c" 1>&6 -echo "configure:12214: checking for GNU ld" >&5 +echo "configure:12324: checking for GNU ld" >&5 fi if test -z "$LTLD"; then @@ -12248,7 +12358,7 @@ # Check to see if it really is or isn't GNU ld. echo $ac_n "checking if the linker is GNU ld""... $ac_c" 1>&6 -echo "configure:12252: checking if the linker is GNU ld" >&5 +echo "configure:12362: checking if the linker is GNU ld" >&5 # I'd rather use --version here, but apparently some GNU ld's only accept -v. if $LTLD -v 2>&1 &5; then xe_gnu_ld=yes @@ -12275,7 +12385,7 @@ # OK - only NOW do we futz about with ld. # See if the linker supports building shared libraries. echo $ac_n "checking whether the linker supports shared libraries""... $ac_c" 1>&6 -echo "configure:12279: checking whether the linker supports shared libraries" >&5 +echo "configure:12389: checking whether the linker supports shared libraries" >&5 dll_ld=$CC dll_ldflags=$LDFLAGS ld_shlibs=yes @@ -12491,10 +12601,10 @@ for ac_func in dlerror _dlerror do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:12495: checking for $ac_func" >&5 - -cat > conftest.$ac_ext <&5 + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:12631: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -12551,11 +12661,11 @@ fi cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 +if { (eval echo configure:12669: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit $?) 2>&5 then : else @@ -12937,10 +13047,10 @@ ac_configure_args="$T" { test "$extra_verbose" = "yes" && cat << EOF - Defining EMACS_CONFIGURATION = "$canonical" + Defining EMACS_CONFIGURATION = "$configuration" EOF cat >> confdefs.h <> confdefs.h <<\EOF +#define PDUMP 1 +EOF +} + ( @@ -13254,15 +13372,20 @@ echo " *WARNING* The Motif menubar implementation is currently buggy." echo " We recommend using the Lucid menubar instead." echo " Re-run configure with --with-menubars='lucid'." ;; + msw ) echo " Using MS-Windows menubars." ;; esac case "$with_scrollbars" in lucid ) echo " Using Lucid scrollbars." ;; motif ) echo " Using Motif scrollbars." ;; athena ) echo " Using Athena scrollbars." ;; athena3d ) echo " Using Athena-3d scrollbars." ;; + msw ) echo " Using MS-Windows scrollbars." ;; esac case "$with_widgets" in motif ) echo " Using Motif native widgets." ;; + athena ) echo " Using Athena native widgets." ;; + athena3d ) echo " Using Athena-3d native widgets." ;; + msw ) echo " Using MS-Windows native widgets." ;; esac case "$with_dialogs" in motif ) @@ -13276,6 +13399,7 @@ ;; athena ) echo " Using Athena dialog boxes." ;; athena3d ) echo " Using Athena-3d dialog boxes." ;; + msw ) echo " Using MS-Windows dialog boxes." ;; esac test "$with_modules" = "yes" && echo " Compiling in DSO module support." test "$with_clash_detection" = yes && \ @@ -13285,8 +13409,9 @@ test "$with_kerberos" = yes && echo " Using Kerberos for POP authentication." test "$with_hesiod" = yes && echo " Using Hesiod to get POP server host." test "$use_union_type" = yes && echo " Using the union type for Lisp_Objects." -test "$debug" = yes && echo " Compiling in extra code for debugging." -test "$usage_tracking" = yes && echo " Compiling with usage tracking active (Sun internal)." +test "$pdump" = yes && echo " Using the new portable dumper (wishful thinking)." +test "$debug" = yes && echo " Compiling in extra code for debugging." +test "$usage_tracking" = yes && echo " Compiling with usage tracking active (Sun internal)." if test "$error_check_extents $error_check_typecheck $error_check_bufpos $error_check_gc $error_check_malloc" \ != "no no no no no"; then echo " WARNING: ---------------------------------------------------------" diff -r 28d9c139be4c -r 11054d720c21 configure.in --- a/configure.in Mon Aug 13 11:25:03 2007 +0200 +++ b/configure.in Mon Aug 13 11:26:11 2007 +0200 @@ -388,6 +388,7 @@ with_tty="" use_union_type="no" with_dnet="" +pdump="no" dnl ------------------ dnl Options Processing @@ -516,6 +517,7 @@ const_is_losing | \ usage_tracking | \ use_union_type | \ + pdump | \ debug | \ use_assertions | \ memory_usage_stats | \ @@ -759,6 +761,8 @@ ;; dnl Obsolete legacy argument? Warn, but otherwise ignore. + "use_minimal_tagbits" | \ + "use_indexed_lrecord_implementation" | \ "run_in_place" | \ "with_gnu_make" ) AC_MSG_WARN([Obsolete option \`--$optname' ignored.]) @@ -1030,6 +1034,7 @@ vax-*-* ) machine=vax ;; mips-dec-* ) machine=pmax ;; mips-sgi-* ) machine=iris4d ;; + mips*-linux ) machine=mips ;; romp-ibm-* ) machine=ibmrt ;; rs6000-ibm-aix* ) machine=ibmrs6000 ;; powerpc-ibm-aix* ) machine=ibmrs6000 ;; @@ -2860,6 +2865,9 @@ dnl XE_APPEND(pkg-src/tree-x, INSTALL_ARCH_DEP_SUBDIR)]) dnl fi + dnl Autodetect -lXaw3d + AC_CHECK_LIB(Xaw3d, XawScrollbarSetThumb, have_xaw3d=yes, have_xaw3d=no) + dnl autodetect Motif - but only add to libs_x later (if necessary) AC_CHECK_HEADER(Xm/Xm.h, [AC_CHECK_LIB(Xm, XmStringFree, have_motif=yes, have_motif=no)], @@ -2888,6 +2896,7 @@ esac case "$with_dialogs" in "" | "yes" | "lucid" ) if test "$have_motif" = "yes"; then with_dialogs="motif" + elif test "$have_xaw3d" = "yes"; then with_dialogs="athena3d" elif test "$have_xaw" = "yes"; then with_dialogs="athena" else with_dialogs=no fi ;; @@ -2895,15 +2904,27 @@ case "$with_scrollbars" in "" | "yes" ) with_scrollbars="lucid" ;; esac -case "$with_widgets" in "" | "yes" ) +case "$with_widgets" in "" | "yes" | "lucid") if test "$have_motif" = "yes"; then with_widgets="motif" + elif test "$have_xaw3d" = "yes"; then with_widgets="athena3d" + elif test "$have_xaw" = "yes"; then with_widgets="athena" else with_widgets=no fi ;; esac all_widgets="$with_menubars $with_scrollbars $with_dialogs $with_toolbars $with_widgets" -case "$all_widgets" in *athena* ) +case "$all_widgets" in + *athena*3d ) + AC_DEFINE(LWLIB_USES_ATHENA) + AC_DEFINE(NEED_ATHENA) + XE_APPEND(lwlib-Xaw.o, lwlib_objs) + if test "$have_xaw3d"; then + XE_PREPEND(-lXaw3d, libs_x) + else + XE_PREPEND(-lXaw, libs_x) + fi ;; + *athena* ) AC_DEFINE(LWLIB_USES_ATHENA) AC_DEFINE(NEED_ATHENA) XE_APPEND(lwlib-Xaw.o, lwlib_objs) @@ -2920,6 +2941,11 @@ test "$with_menubars" = "lucid" && XE_APPEND(xlwmenu.o, lwlib_objs) test "$with_menubars" = "motif" && XE_APPEND(xlwmenu.o, lwlib_objs) test "$with_scrollbars" = "lucid" && XE_APPEND(xlwscrollbar.o, lwlib_objs) +test "$with_widgets" != "no" && test "$with_widgets" != "msw" && \ + XE_APPEND(xlwtabs.o xlwgcs.o, lwlib_objs) +case "$with_widgets" in athena* ) + XE_APPEND(xlwradio.o xlwcheckbox.o xlwgauge.o, lwlib_objs);; +esac case "$all_widgets" in *lucid* ) AC_DEFINE(NEED_LUCID) XE_APPEND(lwlib-Xlw.o, lwlib_objs) ;; @@ -2931,11 +2957,15 @@ case "$with_dialogs" in athena* ) AC_DEFINE(LWLIB_DIALOGS_ATHENA) ;; esac test "$with_scrollbars" = "athena3d" && AC_DEFINE(LWLIB_SCROLLBARS_ATHENA3D) test "$with_dialogs" = "athena3d" && AC_DEFINE(LWLIB_DIALOGS_ATHENA3D) +case "$with_widgets" in athena* ) AC_DEFINE(LWLIB_WIDGETS_ATHENA);; esac +test "$with_widgets" != "no" && test "$with_widgets" != "msw" && \ + AC_DEFINE(LWLIB_TABS_LUCID) test "$with_menubars" != "no" && AC_DEFINE(HAVE_MENUBARS) test "$with_scrollbars" != "no" && AC_DEFINE(HAVE_SCROLLBARS) test "$with_dialogs" != "no" && AC_DEFINE(HAVE_DIALOGS) test "$with_toolbars" != "no" && AC_DEFINE(HAVE_TOOLBARS) +test "$with_widgets" != "no" && AC_DEFINE(HAVE_WIDGETS) test "$with_menubars" = "lucid" && AC_DEFINE(LWLIB_MENUBARS_LUCID) test "$with_scrollbars" = "lucid" && AC_DEFINE(LWLIB_SCROLLBARS_LUCID) @@ -2943,6 +2973,7 @@ test "$with_menubars" = "motif" && AC_DEFINE(LWLIB_MENUBARS_MOTIF) test "$with_scrollbars" = "motif" && AC_DEFINE(LWLIB_SCROLLBARS_MOTIF) test "$with_dialogs" = "motif" && AC_DEFINE(LWLIB_DIALOGS_MOTIF) +test "$with_widgets" = "motif" && AC_DEFINE(LWLIB_WIDGETS_MOTIF) test "$with_menubars" != "no" && XE_ADD_OBJS(menubar.o) test "$with_scrollbars" != "no" && XE_ADD_OBJS(scrollbar.o) @@ -3102,7 +3133,7 @@ XE_COMPUTE_RUNPATH() fi -AC_CHECK_FUNCS(cbrt closedir dup2 eaccess fmod fpathconf frexp ftime gethostname getpagesize gettimeofday getcwd getwd logb lrand48 matherr mkdir mktime perror poll random rename res_init rint rmdir select setitimer setpgid setlocale setsid sigblock sighold sigprocmask snprintf strcasecmp strerror tzset ulimit usleep utimes waitpid vsnprintf) +AC_CHECK_FUNCS(cbrt closedir dup2 eaccess fmod fpathconf frexp ftime gethostname getpagesize gettimeofday getcwd getpt getwd logb lrand48 matherr mkdir mktime perror poll random rename res_init rint rmdir select setitimer setpgid setlocale setsid sigblock sighold sigprocmask snprintf stpcpy strcasecmp strerror tzset ulimit usleep utimes waitpid vsnprintf) dnl realpath is buggy on linux, decosf and aix4 @@ -3962,7 +3993,7 @@ fi XE_SPACE(ac_configure_args, $ac_configure_args) -AC_DEFINE_UNQUOTED(EMACS_CONFIGURATION, "$canonical") +AC_DEFINE_UNQUOTED(EMACS_CONFIGURATION, "$configuration") AC_DEFINE_UNQUOTED(EMACS_CONFIG_OPTIONS, "$ac_configure_args") AC_DEFINE_UNQUOTED(config_machfile, "$machfile") AC_DEFINE_UNQUOTED(config_opsysfile, "$opsysfile") @@ -3998,6 +4029,7 @@ test "$with_kerberos" = "yes" && AC_DEFINE(KERBEROS) test "$with_hesiod" = "yes" && AC_DEFINE(HESIOD) test "$use_union_type" = "yes" && AC_DEFINE(USE_UNION_TYPE) +test "$pdump" = "yes" && AC_DEFINE(PDUMP) dnl ------------------------------- dnl Report on what we decided to do @@ -4132,15 +4164,20 @@ echo " *WARNING* The Motif menubar implementation is currently buggy." echo " We recommend using the Lucid menubar instead." echo " Re-run configure with --with-menubars='lucid'." ;; + msw ) echo " Using MS-Windows menubars." ;; esac case "$with_scrollbars" in lucid ) echo " Using Lucid scrollbars." ;; motif ) echo " Using Motif scrollbars." ;; athena ) echo " Using Athena scrollbars." ;; athena3d ) echo " Using Athena-3d scrollbars." ;; + msw ) echo " Using MS-Windows scrollbars." ;; esac case "$with_widgets" in motif ) echo " Using Motif native widgets." ;; + athena ) echo " Using Athena native widgets." ;; + athena3d ) echo " Using Athena-3d native widgets." ;; + msw ) echo " Using MS-Windows native widgets." ;; esac case "$with_dialogs" in motif ) @@ -4154,6 +4191,7 @@ ;; athena ) echo " Using Athena dialog boxes." ;; athena3d ) echo " Using Athena-3d dialog boxes." ;; + msw ) echo " Using MS-Windows dialog boxes." ;; esac test "$with_modules" = "yes" && echo " Compiling in DSO module support." test "$with_clash_detection" = yes && \ @@ -4163,8 +4201,9 @@ test "$with_kerberos" = yes && echo " Using Kerberos for POP authentication." test "$with_hesiod" = yes && echo " Using Hesiod to get POP server host." test "$use_union_type" = yes && echo " Using the union type for Lisp_Objects." -test "$debug" = yes && echo " Compiling in extra code for debugging." -test "$usage_tracking" = yes && echo " Compiling with usage tracking active (Sun internal)." +test "$pdump" = yes && echo " Using the new portable dumper (wishful thinking)." +test "$debug" = yes && echo " Compiling in extra code for debugging." +test "$usage_tracking" = yes && echo " Compiling with usage tracking active (Sun internal)." if test "$error_check_extents $error_check_typecheck $error_check_bufpos $error_check_gc $error_check_malloc" \ != "no no no no no"; then echo " WARNING: ---------------------------------------------------------" diff -r 28d9c139be4c -r 11054d720c21 configure.usage --- a/configure.usage Mon Aug 13 11:25:03 2007 +0200 +++ b/configure.usage Mon Aug 13 11:26:11 2007 +0200 @@ -159,6 +159,9 @@ and localdir files in case run-time searching for them fails. --moduledir=DIR Directory to install dynamic modules in. +--pdump New, experimental, non-working, don't-sue-me-if- + your-house-collapses-and-your-wife-goes-away, + portable dumper. Internationalization options: diff -r 28d9c139be4c -r 11054d720c21 etc/DISTRIB --- a/etc/DISTRIB Mon Aug 13 11:25:03 2007 +0200 +++ b/etc/DISTRIB Mon Aug 13 11:26:11 2007 +0200 @@ -1,8 +1,8 @@ -*- text -*- - XEmacs availability information. Last Modified: 17-Apr-97. + XEmacs availability information. Last Modified: 18-Jul-99. -XEmacs is available via anonymous FTP from ftp.xemacs.org (128.174.252.16) +XEmacs is available via anonymous FTP from ftp.xemacs.org (207.96.122.8) in the directory /pub/xemacs/. ftp.xemacs.org is the primary distribution point, but you may find diff -r 28d9c139be4c -r 11054d720c21 etc/NEWS --- a/etc/NEWS Mon Aug 13 11:25:03 2007 +0200 +++ b/etc/NEWS Mon Aug 13 11:26:11 2007 +0200 @@ -33,30 +33,6 @@ * Changes in XEmacs 21.2 ======================== -** The functions in rect.el have been almost completely rewritten... -to avoid inserting undesirable spaces, notably at the end of lines. -Two typical examples of this old behavior are `string-rectangle', which filled -all lines up to the right side of the rectangle, and `clear-rectangle', which -filled even empty lines up to the left side. - -This is not the case any more. All these functions have been rewritten to -avoid inserting unwanted spaces, and an optional prefix now allows them to -behave the old way. - -As a side effect, `move-to-column' now also accepts 'coerce as its second -argument, meaning that the line shouldn't be filled if its too short to reach -the desired column. - -** You can now customize and save comments for faces and variables. - -In Custom buffers, a new menu entry allows you to add and edit a comment. -Comments for variables can also be assigned by calling -`customize-set-(value|variable)' with a prefix argument. - -** XEmacs now locates the early package hierarchy at ~/.xemacs/packages. - -This has changed from simply ~/.xemacs. - ** `delete-key-deletes-forward' now defaults to t. `delete-key-deletes-forward' is the variable that regulates the @@ -83,6 +59,33 @@ searches, like `zap-to-char', `list-matching-lines', `tags-search' etc. The incremental search facility has always behaved that way. +** The rectangle functions have been almost completely rewritten in +order to avoid inserting undesirable spaces, notably at the end of +lines. Two typical examples of the old behavior were +`string-rectangle', which filled all lines up to the right side of the +rectangle, and `clear-rectangle', which filled even empty lines up to +the left side. All functions have been rewritten to avoid inserting +unwanted spaces, and an optional prefix now allows them to behave the +old way. + +As a side effect, the FORCE argument to `move-to-column' now +understands the special value `coerce', which means that the line +should not be filled if it is too short to reach the desired column. + +** Incremental search will now highlight all visible matches, making +it easier to anticipate where consecutive C-s or C-r will place the +point. If you want to disable the feature, set +`isearch-highlight-all-matches' to nil. + +** You can now customize and save comments for faces and variables. +In Custom buffers, a new menu entry allows you to add and edit a +comment. Comments for variables can also be assigned by calling +`customize-set-(value|variable)' with a prefix argument. + +** XEmacs now locates the early package hierarchies at +~/.xemacs/mule-packages/ and ~/.xemacs/xemacs-packages/. Previously, +the early packages were located in ~/.xemacs/. + ** You can now create "indirect buffers", like in GNU Emacs. An indirect buffer shares its text with another buffer ("base buffer"), but has its own major mode, local variables, extents, and narrowing. @@ -115,20 +118,19 @@ ** Native widgets can be displayed in buffers. The glyph system has been extended to allow the display of glyphs that -are implemented as native window-system widgets. Thus you can embed +are implemented as native window-system widgets. Thus you can embed buttons, scrollbars, combo boxes, edit fields and progress gauges in a -buffer. As a side effect subwindow support now works once again. +buffer. As a side effect subwindow support now works once again. This support is currently only available under MS-Windows. -** X-Face support is now available under MS-Windows - +** X-Face support is now available under MS-Windows. If an X-Face libary built under MS-Windows is available then XEmacs will use this at build time. -** The font-menu is now available under MS-Windows +** The font-menu is now available under MS-Windows. -** MS-Windows support for selection is much more robust +** MS-Windows support for selection is now much more robust. Generally selection should now do what you would expect under MS-Windows: the middle mouse button will paste your current selection @@ -137,9 +139,17 @@ per X. The only thing selection doesn't do is set the clipboard automatically -as this would break the MS-Windows model. If you want this behaviour +as this would break the MS-Windows model. If you want this behaviour then set `selection-sets-clipboard' to t +** New command-line switches -user-init-file and -user-init-directory. +These can be used to specify alternate locations for what is normally +~/.emacs and ~/.xemacs. + +Moreover, -user (which used to only work in unpredictable ways) +is now equivalent to +-user-init-file ~/.emacs -user-init-directory ~/.xemacs. + * Lisp and internal changes in XEmacs 21.2 ========================================== @@ -270,6 +280,13 @@ `base64-encode-region', `base64-encode-string', `base64-decode-region' and `base64-decode-string'. +** user-init-directory is now an absolute, unexpanded path. +Previously, `user-init-directory' used to be relative to +(concat "~" init-file-user). This turned out to be too complicated +for most packages (and some core Lisp files) to use correctly. + +Also, `init-file-user' has been obsoleted in the process. + * Changes in XEmacs 21.0 ======================== @@ -752,7 +769,7 @@ Look under "Startup Paths" in the Info documentation for more information. -*** site-lisp is now longer part of the load-path by default. +*** site-lisp is no longer part of the load-path by default. Its use is deprecated, but you can specify --with-site-lisp=yes at the configure command line to get it back. diff -r 28d9c139be4c -r 11054d720c21 lib-src/ChangeLog --- a/lib-src/ChangeLog Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/ChangeLog Mon Aug 13 11:26:11 2007 +0200 @@ -1,3 +1,44 @@ +1999-11-10 XEmacs Build Bot + + * XEmacs 21.2.20 is released + +1999-11-04 Martin Buchholz + + * gnuserv.c (handle_response): Warning suppression + +1999-09-27 Martin Buchholz + + * ellcc.c: + ANSIfy. + Remove MSDOS cruft. + Remove WINDOWS cruft. + Remove VMS cruft. + (main): The wrong number of bytes were being read during argument + processing. + Delete ANSI imitations like ellcc_strchr(). + Call functions with the right number of arguments. + Fix a typo. + Make functions static. + Remove compiler warnings. + +1999-09-22 Martin Buchholz + + * cvtmail.c (main): ANSIfy + * digest-doc.c (main): ANSIfy + * hexl.c (main): ANSIfy + + * make-path.c: Remove declaration for errno. + * mmencode.c (nextcharin): ANSIfy + * movemail.c (pop_retr): ANSIfy + +1999-07-30 Gleb Arshinov + + * pop.c (pop_quit): use CLOSESOCKET() instead of close() + + * run.c (build_cmdline): Fix NT native build unreferenced variable + warning + (WinMain): Fix release mode build unreferenced variable warning + 1999-07-30 XEmacs Build Bot * XEmacs 21.2.19 is released diff -r 28d9c139be4c -r 11054d720c21 lib-src/cvtmail.c --- a/lib-src/cvtmail.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/cvtmail.c Mon Aug 13 11:26:11 2007 +0200 @@ -53,9 +53,7 @@ static void error (CONST char *s1, CONST char *s2); int -main (argc, argv) - int argc; - char *argv[]; +main (int argc, char *argv[]) { char *hd; char *md; diff -r 28d9c139be4c -r 11054d720c21 lib-src/digest-doc.c --- a/lib-src/digest-doc.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/digest-doc.c Mon Aug 13 11:26:11 2007 +0200 @@ -11,7 +11,7 @@ #include int -main () +main (int argc, char *argv[]) { register int ch; register int notfirst = 0; diff -r 28d9c139be4c -r 11054d720c21 lib-src/ellcc.c --- a/lib-src/ellcc.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/ellcc.c Mon Aug 13 11:26:11 2007 +0200 @@ -24,8 +24,8 @@ /* Here's the scoop. We would really like this to be a shell script, but -the various Windows platforms dont have reliable scripting that suits -our needs. We dont want to reply on perl or some other such language +the various Windows platforms don't have reliable scripting that suits +our needs. We don't want to rely on perl or some other such language so we have to roll our own executable to act as a front-end for the compiler. @@ -58,87 +58,30 @@ See the samples for more details. */ +#include <../src/config.h> #include #include - -#ifdef MSDOS -# include -# include -# include -# ifndef HAVE_CONFIG_H -# define DOS_NT -# include -# endif -#endif /* MSDOS */ - -#ifdef WINDOWSNT -# include -# include -# include -# include -# define MAXPATHLEN _MAX_PATH -# ifdef HAVE_CONFIG_H -# undef HAVE_NTGUI -# else -# define DOS_NT -# define HAVE_GETCWD -# endif /* not HAVE_CONFIG_H */ -#endif /* WINDOWSNT */ - -#ifdef HAVE_CONFIG_H -# include - /* On some systems, Emacs defines static as nothing for the sake - of unexec. We don't want that here since we don't use unexec. */ -# undef static -#endif /* HAVE_CONFIG_H */ - -#if !defined (WINDOWSNT) && defined (STDC_HEADERS) -#include #include -#endif +#include +#include +#include #ifdef HAVE_UNISTD_H # include -#else -# ifdef HAVE_GETCWD - extern char *getcwd (); -# endif #endif /* HAVE_UNISTD_H */ -#include -#include -#include -#ifndef errno - extern int errno; -#endif -#include -#include - #define EMODULES_GATHER_VERSION #include "emodules.h" #include "ellcc.h" -#if !defined (S_ISREG) && defined (S_IFREG) -# define S_ISREG(m) (((m) & S_IFMT) == S_IFREG) -#endif - -/* Exit codes for success and failure. */ -#ifdef VMS -# define GOOD 1 -# define BAD 0 -#else -# define GOOD 0 -# define BAD 1 -#endif - #define DEBUG #ifndef HAVE_SHLIB int -main() +main (int argc, char *argv[]) { fprintf (stderr, "Dynamic modules not supported on this platform\n"); - return (BAD); + return EXIT_FAILURE; } #else @@ -163,11 +106,12 @@ # define xnew(n,Type) ((Type *) xmalloc ((n) * sizeof (Type))) # define xrnew(op,n,Type) ((Type *) xrealloc ((op), (n) * sizeof (Type))) #endif -long *xmalloc (), *xrealloc (); -void fatal (), pfatal (); -char *ellcc_strchr (), *ellcc_strrchr (); -void add_to_argv (); -void do_compile_mode(), do_link_mode(), do_init_mode(); +static void *xmalloc (size_t); +static void fatal (char *, char *); +static void add_to_argv (CONST char *); +static void do_compile_mode (void); +static void do_link_mode (void); +static void do_init_mode (void); #define SSTR(S) ((S)?(S):"") @@ -196,9 +140,7 @@ STR = DFLT int -main (argc, argv) - int argc; - char *argv[]; +main (int argc, char *argv[]) { char *tmp; int i, done_mode = 0; @@ -207,11 +149,11 @@ prog_argv = argv; #if defined(MSDOS) || defined(WINDOWSNT) - tmp = ellcc_strrchr (argv[0], '\\'); + tmp = strrchr (argv[0], '\\'); if (tmp != (char *)0) tmp++; #elif !defined (VMS) - tmp = ellcc_strrchr (argv[0], '/'); + tmp = strrchr (argv[0], '/'); if (tmp != (char *)0) tmp++; #else @@ -248,7 +190,7 @@ char *modeopt = argv[i] + 7; if (done_mode && strcmp (modeopt, "verbose")) - fatal ("more than one mode specified"); + fatal ("more than one mode specified", (char *) 0); if (strcmp (modeopt, "link") == 0) { done_mode++; @@ -287,13 +229,13 @@ printf ("%s\n", ELLCC_CONFIG); return 0; } - else if (strncmp (argv[i], "--mod-name=", 10) == 0) + else if (strncmp (argv[i], "--mod-name=", 11) == 0) mod_name = argv[i] + 11; - else if (strncmp (argv[i], "--mod-title=", 11) == 0) + else if (strncmp (argv[i], "--mod-title=", 12) == 0) mod_title = argv[i] + 12; - else if (strncmp (argv[i], "--mod-version=", 13) == 0) + else if (strncmp (argv[i], "--mod-version=", 14) == 0) mod_version = argv[i] + 14; - else if (strncmp (argv[i], "--mod-output=", 12) == 0) + else if (strncmp (argv[i], "--mod-output=", 13) == 0) mod_output = argv[i] + 13; else { @@ -339,7 +281,7 @@ #endif if (exec_argc < 2) - fatal ("too few arguments"); + fatal ("too few arguments", (char *) 0); /* * Get the over-rides from the environment @@ -378,83 +320,23 @@ } /* Like malloc but get fatal error if memory is exhausted. */ -long * -xmalloc (size) - unsigned int size; +static void * +xmalloc (size_t size) { - long *result = (long *) malloc (size); + void *result = malloc (size); if (result == NULL) - fatal ("virtual memory exhausted", (char *)NULL); - return result; -} - -long * -xrealloc (ptr, size) - char *ptr; - unsigned int size; -{ - long *result = (long *) realloc (ptr, size); - if (result == NULL) - fatal ("virtual memory exhausted", (char *)NULL); + fatal ("virtual memory exhausted", (char *)0); return result; } /* Print error message and exit. */ -void -fatal (s1, s2) - char *s1, *s2; +static void +fatal (char *s1, char *s2) { fprintf (stderr, "%s: ", progname); fprintf (stderr, s1, s2); fprintf (stderr, "\n"); - exit (BAD); -} - -void -pfatal (s1) - char *s1; -{ - perror (s1); - exit (BAD); -} - -/* - * Return the ptr in sp at which the character c last - * appears; NULL if not found - * - * Identical to System V strrchr, included for portability. - */ -char * -ellcc_strrchr (sp, c) - register char *sp, c; -{ - register char *r; - - r = NULL; - do - { - if (*sp == c) - r = sp; - } while (*sp++); - return r; -} - -/* - * Return the ptr in sp at which the character c first - * appears; NULL if not found - * - * Identical to System V strchr, included for portability. - */ -char * -ellcc_strchr (sp, c) - register char *sp, c; -{ - do - { - if (*sp == c) - return sp; - } while (*sp++); - return NULL; + exit (EXIT_FAILURE); } /* @@ -462,9 +344,8 @@ * to the compiler or linker. We need to split individual words into * arguments, taking quoting into account. This can get ugly. */ -void -add_to_argv (str) - CONST char *str; +static void +add_to_argv (CONST char *str) { int sm = 0; CONST char *s = (CONST char *)0; @@ -557,8 +438,8 @@ * is build up the argument vector and exec() it. We must just make sure * that we get all of the required arguments in place. */ -void -do_compile_mode() +static void +do_compile_mode (void) { int i; char ts[4096]; /* Plenty big enough */ @@ -587,8 +468,8 @@ * all of the provided arguments, then the final post arguments. Once * all of this has been done, the argument vector is ready to run. */ -void -do_link_mode() +static void +do_link_mode (void) { int i,x; char *t, ts[4096]; /* Plenty big enough */ @@ -648,8 +529,8 @@ * the header information first, as make-doc will append to the file by * special dispensation. */ -void -do_init_mode() +static void +do_init_mode (void) { int i; char ts[4096]; /* Plenty big enough */ diff -r 28d9c139be4c -r 11054d720c21 lib-src/gnuserv.c --- a/lib-src/gnuserv.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/gnuserv.c Mon Aug 13 11:26:11 2007 +0200 @@ -323,7 +323,7 @@ char buf[GSERV_BUFSZ+1]; int offset=0; int s; - int len; + int len = 0; int result_len; /* read in "n/m:" (n=client fd, m=message length) */ diff -r 28d9c139be4c -r 11054d720c21 lib-src/hexl.c --- a/lib-src/hexl.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/hexl.c Mon Aug 13 11:26:11 2007 +0200 @@ -29,9 +29,7 @@ void usage (void); int -main(argc, argv) - int argc; - char *argv[]; +main (int argc, char *argv[]) { register long address; char string[18]; diff -r 28d9c139be4c -r 11054d720c21 lib-src/make-path.c --- a/lib-src/make-path.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/make-path.c Mon Aug 13 11:26:11 2007 +0200 @@ -35,8 +35,6 @@ #include #include -extern int errno; - char *prog_name; static int touchy_mkdir (char *path) diff -r 28d9c139be4c -r 11054d720c21 lib-src/mmencode.c --- a/lib-src/mmencode.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/mmencode.c Mon Aug 13 11:26:11 2007 +0200 @@ -52,9 +52,7 @@ static int InNewline=0; static int -nextcharin(infile, PortableNewlines) -FILE *infile; -int PortableNewlines; +nextcharin (FILE *infile, int PortableNewlines) { int c; diff -r 28d9c139be4c -r 11054d720c21 lib-src/movemail.c --- a/lib-src/movemail.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/movemail.c Mon Aug 13 11:26:11 2007 +0200 @@ -150,7 +150,8 @@ static long *xmalloc (unsigned int); #ifdef MAIL_USE_POP static int popmail (char *, char *, char *); -static int pop_retr (popserver server, int msgno, int (*action)(), void *arg); +static int pop_retr (popserver server, int msgno, + int (*action)(char *, FILE *), void *arg); static int mbx_write (char *, FILE *); static int mbx_delimit_begin (FILE *); static int mbx_delimit_end (FILE *); @@ -730,7 +731,7 @@ } static int -pop_retr (popserver server, int msgno, int (*action)(), void *arg) +pop_retr (popserver server, int msgno, int (*action)(char *, FILE *), void *arg) { char *line; int ret; diff -r 28d9c139be4c -r 11054d720c21 lib-src/pop.c --- a/lib-src/pop.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/pop.c Mon Aug 13 11:26:11 2007 +0200 @@ -922,7 +922,7 @@ ret = -1; } - close (server->file); + CLOSESOCKET (server->file); } if (server->buffer) diff -r 28d9c139be4c -r 11054d720c21 lib-src/run.c --- a/lib-src/run.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lib-src/run.c Mon Aug 13 11:26:11 2007 +0200 @@ -65,10 +65,14 @@ char execpath[MAX_PATH]; char* argv[MAX_ARGS+1]; /* leave extra slot for compact_invocation argv[0] */ int argc; - int i,j; + int i; char exec[MAX_PATH + FILENAME_MAX + 100]; char cmdline2[MAX_ARGS * MAX_PATH]; +#ifdef Debug + int j; +#endif + compact_invocation = get_exec_name_and_path(execname,execpath); if (compact_invocation) @@ -157,7 +161,9 @@ char* p; char* p2; char exec2[MAX_PATH + FILENAME_MAX + 100]; +#if defined(__CYGWIN__) char tmp[MAX_PATH + FILENAME_MAX + 100]; +#endif strcpy(exec2,exec); /* this depends on short-circuit evaluation */ if ( ((p = strrchr(exec2,'\\')) && stricmp(p,"\\xemacs") == 0) || diff -r 28d9c139be4c -r 11054d720c21 lisp/.cvsignore --- a/lisp/.cvsignore Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/.cvsignore Mon Aug 13 11:26:11 2007 +0200 @@ -1,1 +1,2 @@ +ChangeLog.font-menu finder-inf.el diff -r 28d9c139be4c -r 11054d720c21 lisp/ChangeLog --- a/lisp/ChangeLog Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/ChangeLog Mon Aug 13 11:26:11 2007 +0200 @@ -1,3 +1,568 @@ +1999-11-10 XEmacs Build Bot + + * XEmacs 21.2.20 is released + +1999-11-06 Hrvoje Niksic + + * setup-paths.el (paths-default-info-directories): Add + /usr/share/info and /usr/local/share/info. + +1999-10-30 Hrvoje Niksic + + * about.el: Updated Vladimir Ivanovic's info. + +11999-08-28 Jan Vroonhof + + * auto-show.el (auto-show-truncationp): Remove. + + * auto-show.el (auto-show-should-take-action-p): Use window-truncated-p + +999-09-23 Gunnar Evermann + + * indent.el (indent-line-to): fix bug: spaces were not replaced + with tab if column is multiple of tab-width + From dhn@qedinc.com + +1999-10-24 Jan Vroonhof + + * mule/mule-cmds.el (read-input-method-name): Accept symbols + correctly. Patch from Mikio Nakajima + + * package-get.el (package-get-package-provider): Be verbose when + interactive. Patch from Robert Pluim + +1999-08-23 Mike McEwan + + * info.el (Info-suffix-list): Add ".info.bz2" to the recognised + info file suffixes. + +1999-08-19 Stephen Tse + + * process.el (open-network-stream): Add a new optional parameter + PROTOCOL to support udp; fix a minor typo and add an explanation + in docstring for udp programming. + + * code-process.el (open-network-stream): Add a new optional + parameter PROTOCOL to support udp; fix a minor typo and add an + explanation in docstring for udp programming. + +1999-10-18 Andy Piper + + * gui.el (make-gui-button): be more precise about how we call + callbacks. + + * wid-edit.el (widget-push-button-value-create): Use the new form + of native gui-button. + +1999-10-14 Yoshiki Hayashi + + * info.el (Info-page-prev): Don't do (sit-for 0). + +1999-10-13 Andy Piper + + * gutter-items.el (progress-abort-glyph): new glyph for showing + abort status. + (append-progress): dispatch-event rather than sit-for. + (abort-progress): new function. Show the abort glyph with an + appropriate message. + (raw-append-progress): dispatch-event rather than sit-for. + (display-progress): cope with aborts. + + * gui.el (make-gui-button): Use native widgets for buttons + unconditionally. + (insert-gui-button): ditto. + (gui-button-p): ditto. + + * xbm-button.el: remove from core. + + * xpm-button.el: remove from core. + +1999-10-07 Olivier Galibert + + * faces.el (init-device-faces): Don't initialize the random faces + on the stream device. + +1999-10-06 Andy Piper + + * files.el (recover-file): Don't use ls under windows for revert buffer. + +1999-09-25 Adrian Aichner + + * package-get.el (package-get-download-menu): Make menu really + toggle download sites. + (package-get-download-sites): Add autoload cookie. + +1999-09-29 Michael Sperber [Mr. Preprocessor] + + * setup-paths.el (paths-find-module-directory): Ditto. + +1999-09-29 Werner Fink + + * setup-paths.el (paths-find-exec-directory): Add missing nil + parameter for environment. + +1999-09-27 Martin Buchholz + + * modeline.el (modeline-format): + Only purecopy the strings. Else + (nsublis '(("%p" . "%P")) (default-value 'modeline-format) :test 'equal) + barfs. + +1999-08-28 Mike Woolley + + * winnt.el: Removed nt-shell-mode-hook, which was preventing the + user setting comint-completion-addsuffix and + comint-process-echoes. + +1999-09-22 Andy Piper + + * gutter-items.el (update-tab-in-gutter): use + last-nonminibuf-window instead of selected-window. + +1999-09-18 Andy Piper + + * gnuserv.el (gnuserv-edit-files): select frame we are going to + display on. + + * subr.el (record-buffer-hook): new variable so that the hook gets + some documentation. + +1999-09-16 Andy Piper + + * gutter-items.el (update-tab-in-gutter): only update when the + gutter is visible. + (remove-buffer-from-gutter-tab): ditto. + +1999-09-17 Hrvoje Niksic + + * simple.el (do-auto-fill): Commented out part of Kinsoku + processing. + +1999-09-14 Hrvoje Niksic + + * isearch-mode.el (isearch-highlightify-region): Give the + highlighting extents a high priority. + (isearch-make-extent): Give the main highlighting extent an even + higher priority. + +1999-09-13 Michael Sperber [Mr. Preprocessor] + + * packages.el (packages-compute-package-locations): Fix typo from + -u rationalization. + +1999-09-11 Michael Sperber [Mr. Preprocessor] + + * setup-paths.el (paths-find-doc-directory): Respect value of + `configure-doc-directory.' + + * find-paths.el (paths-find-architecture-directory): Give + precendence `default' argument (which typically comes from + configure). + +1999-09-05 Michael Sperber [Mr. Preprocessor] + + * startup.el (command-line-early): Added options -user-init-file + and -user-init-directory. + + * files.el (user-init-file): Default to NIL so we can recognize + when it's set. + +1999-08-30 Michael Sperber [Mr. Preprocessor] + + * obsolete.el (init-file-user): + * startup.el: + * packages.el (packages-compute-package-locations): + * package-get.el (package-get-user-index-filename): + * menubar-items.el (maybe-add-init-button): + * info.el (Info-annotations-path): + * dump-paths.el: + Change `user-init-directory' to be an absolute path. + Use `user-init-directory' where appropriate. + Zap `init-file-user' and its uses. + +1999-09-09 Hrvoje Niksic + + * subr.el (copy-symbol): New function. + +1999-09-08 Hrvoje Niksic + + * isearch-mode.el (isearch-done): Be sure to restore invisible + extents in the proper buffer. + (isearch-pre-command-hook): Set this-command to the correct value + in case the buffer has changed and old overriding-local-map was + used. + (isearch-restore-extent): Use remprop instead of setting the + property to nil. + +1999-09-08 Hrvoje Niksic + + * cmdloop.el (execute-extended-command): Update zmacs region + before the delay. + (execute-extended-command): Make the message gettext-friendly. + +1999-09-07 Andy Piper + + * gutter-items.el (progress-gauge-glyph): renamed from + progress-glyph. + (progress-text-glyph): new variable. + (progress-layout-glyph): use layouts and text glyphs. + (progress-area-buffer): removed. + (progress-text-and-extent): new variable. + (progress-displayed-p): dynamically create gutter area buffer. + (clear-progress): ditto. + (raw-append-progress): ditto. + (append-progress): use new glyph names. + (raw-append-progress): only create the extent when needed. set + properties more optimally. + (progress): remove args. + +1999-09-07 Hrvoje Niksic + + * isearch-mode.el (isearch-range-invisible): Use mapc instead of + mapcar where the return value is unused. + (isearch-restore-invisible-extents): Ditto. + (isearch-highlight-all-cleanup): Ditto. + (isearch-delete-extents-in-range): Traverse the extents only once. + (isearch-highlight-all-update): Don't start over if the search + string has changed and more input is pending. + +1999-09-07 Hrvoje Niksic + + * packages.el (packages-find-package-data-path): Ditto. + + * cl.el: Use mapcar at top-level -- mapc is no longer a subr. + + * subr.el (mapc-internal): Don't make obsolete. + + * cl-extra.el (mapc): Resurrect. + +1999-09-03 Hrvoje Niksic + + * obsolete.el (isearch-yank-x-clipboard): Define it as an obsolete + alias. + + * isearch-mode.el (isearch-top-state): Restore isearch-word. + (isearch-yank-clipboard): Renamed from isearch-yank-x-clipboard. + (isearch-yank-clipboard): Use get-clipboard instead of + x-get-clipboard. + (isearch-yank-selection): Fix docstring. + +1999-09-02 Martin Buchholz + + * cl-extra.el: Obsolete hash-table-type in favor of hash-table-weakness. + +1999-09-02 Hrvoje Niksic + + * cl-macs.el (extent-start-position): Fix setf method. + (extent-end-position): Ditto. + +1999-09-02 Hrvoje Niksic + + * isearch-mode.el: End merge with FSF 20.4. + + * isearch-mode.el (search-invisible): New variable. + (isearch-hide-immediately): Ditto. + (isearch-unhidden-extents): Ditto. + (isearch-range-invisible): New function. + (isearch-unhide-extent): Ditto. + (isearch-restore-invisible-extents): Ditto. + (isearch-restore-extent): Ditto. + + * isearch-mode.el (isearch-ring-advance-edit): Use FSF + implementation. + (isearch-ring-retreat-edit): Ditto. + (isearch-forward): New argument NO-RECURSIVE-EDIT. + (isearch-forward-regexp): New arguments NOT-REGEXP and + NO-RECURSIVE-EDIT. + (isearch-backward): New argument NO-RECURSIVE-EDIT. + (isearch-backward-regexp): New arguments NOT-REGEXP and + NO-RECURSIVE-EDIT. + (isearch-mode): Return isearch-success. + (isearch-update): Use unread-command-events instead of + unread-command-event. + (isearch-abort): If an invalid regexp is encountered, keep popping + states. + (isearch-*-char): Use FSF implementation. + (isearch-whitespace-chars): Use the more robust FSF's + implementation. + (isearch-within-brackets): New variable. + (isearch-mode): Initialize it. + (isearch-edit-string): Bind it. + (isearch-search-and-update): Set it. + (isearch-push-state): Push it. + (isearch-top-state): Pop it. + (isearch-search): Set it. + (isearch-printing-char): When called by isearch-whitespace-chars, + handle M-SPC gracefully. + (isearch-message-prefix): New argument ELLIPSIS. + (isearch-message-suffix): Ditto. + (isearch-message): Use the ELLIPSIS argument when calling + isearch-message-prefix and isearch-message-suffix. + (isearch-message-prefix): Distinguish between "wrapped" and + "overwrapped" search, FWIW. + +1999-09-01 Hrvoje Niksic + + * isearch-mode.el (isearch-edit-string): Use the head of the + search ring instead of search-last-string and search-last-regexp. + (search-highlight): Renamed from isearch-highlight. + (isearch-exit): Use the new name. + (isearch-highlight): Ditto. + (isearch-dehighlight): Ditto. + (isearch-update-ring): New function. + (isearch-done): Call it. + (isearch-done): New argument EDIT. + (isearch-repeat): If search string is empty, look up at the car of + the search ring; ignore the yank pointer. + (isearch-abort): Call isearch-done with NOPUSH. + (isearch-cancel): New function. + (isearch-mode-map): Bind it to ESC ESC ESC. + + * isearch-mode.el: Begin merge with FSF 20.4. + +1999-09-01 Andy Piper + + * x-select.el (x-get-clipboard): obsolete. + (x-yank-clipboard-selection): obsolete + + * select.el (disown-selection): need to be careful to disown the + clipboard if we set it via selection. + (get-clipboard): move from x-select.el + (yank-clipboard-selection): ditto. + +1999-09-01 Hrvoje Niksic + + * isearch-mode.el (isearch-exit): Bind isearch-highlight and + isearch-highlight-all-matches to nil. + (isearch-fixed-case): New variable. + (isearch-mode): Initialize it. + (isearch-edit-string): Save it. + (isearch-toggle-case-fold): Set it. + (isearch-fix-case): Make sure isearch-toggle-case-fold works -- + need to check isearch-fixed-case. + (isearch-toggle-case-fold): Update highlighting of all matches + before the pause. + (isearch-edit-string): + +1999-09-01 Hrvoje Niksic + + * isearch-mode.el (isearch-edit-string): Call isearch-message + before reading the event so that the prompt is displayed properly. + (isearch-message): Use isearch-nonincremental when calling + isearch-message-prefix. + (minibuffer-local-isearch-map): Bind up and down to do the same as + M-p and M-n respectively. + (isearch-done): New arg NOPUSH. + (isearch-edit-string): Use it. + (isearch-edit-string): Don't bind isearch-string. + (isearch-ring-adjust): Edit string, *then* push state. + +1999-08-31 Hrvoje Niksic + + * faces.el (isearch-secondary): Make isearch-secondary look + different than default. + +1999-08-30 Hrvoje Niksic + + * isearch-mode.el (isearch-yank): Use progn instead of the inner + save-excursion. + (isearch-dehighlight): Remove TOTALLY. Simplify. + (isearch-update): Call isearch-dehighlight without arguments. + (isearch-done): Ditto. + + * isearch-mode.el (isearch-fix-case): If the search string has no + upper-case letters, allow the folding to be reenabled. + Previously, once disabled, the folding would remain that way until + the end of isearch. + (isearch-top-state): Call isearch-fix-case. + + * isearch-mode.el (isearch-yank): Use progn instead of the inner + save-excursion. + (isearch-dehighlight): Remove TOTALLY. Simplify. + +1999-08-31 Jan Vroonhof + + * xpm-button.el: + xbm-button.el: Need to exist in core because gui.el depends on + them. + +1999-08-31 Andy Piper + + * gutter-items.el (buffers-tab-face): new customizable variable. + (buffers-tab-default-buffer-line-length): new specifier for + maximum viewable characters. + (progress-stack): new variable for implementing widget-based + progress messages. + (progress-area-buffer): ditto. + (progress-glyph-height): ditto. + (progress-stop-callback): ditto. + (progress-quit-function): new function. + (progress-glyph): new variable. + (progress-layout-glyph): ditto. + (progress-displayed-p): new function, see message-displayed-p for + details. + (clear-progress): ditto. + (remove-progress): ditto. + (append-progress): ditto. + (raw-append-progress): ditto. + (display-progress): ditto. + (current-progress): ditto. + (current-progress-label): ditto. + (progress): ditto. + (lprogress): ditto. + + +1999-08-29 Hrvoje Niksic + + * obsolete.el (isearch-yank-x-selection): Define obsolete alias. + + * isearch-mode.el (isearch-yank-x-selection): Renamed to + `isearch-yank-selection'. + (isearch-mode-map): Use it. + (isearch-yank-selection): Use `get-selection' instead of + `get-x-selection'. + +1999-08-29 Hrvoje Niksic + + * faces.el (isearch-secondary): Create face here. + + * isearch-mode.el: Rewrote the "lazy highlighting" code not to use + timers. + +1999-08-27 Hrvoje Niksic + + * subr.el (buffer-string): More robust backward compatibility + check, courtesy William Perry. + +1999-08-26 Hrvoje Niksic + + * replace.el (perform-replace): Stop the search after the search + limit has been reached. + +1999-08-23 Andy Piper + + * gutter-items.el (update-tab-in-gutter): call add-tab-to-gutter + here if we don't have one. + +1999-08-15 Oscar Figueiredo + + * ldap.el (ldap-coding-system): Default to nil until we get + efficient UTF8 support + (ldap-decode-string): Guard against `decode-coding-string' not + being defined + (ldap-encode-string): Guard against `encode-coding-string' not + being defined + +1999-08-23 Didier Verna + + * rect.el: Cosmetics suggested by Dave Love . + Some doc strings improvements, and add a star to the `interactive' + calls. + +1999-08-18 Stef Epardaud + + * font-lock.el (java-font-lock-keywords-3): introduced new + keywords and regexpes for javadoc syntax 1.2. + +1999-08-17 Andy Piper + + * gutter-items.el (buffers-tab-format-buffer-line-function): use + format-buffers-tab-line. + (buffers-tab-max-buffer-line-length): new variable. + (format-buffers-tab-line): new function. truncate names if over + buffers-tab-max-buffer-line-length. + +1999-08-13 Charles G Waldman + + * cus-start.el: Customize the variable `bell-inhibit-time'. + +1999-08-16 Andy Piper + + * gutter-items.el (remove-buffer-from-gutter-tab): take a + brute-force approach to deleting the last buffer. + (buffers-tab-grouping-regexp): new customizable variable. + (select-buffers-tab-buffers-by-mode): use it. + +1999-08-13 Andy Piper + + * gutter-items.el (remove-buffer-from-gutter-tab): fix *scratch* + deletion problem. + +1999-07-30 Didier Verna + + * cus-edit.el (custom-save-variables): I said, use prin1 instead + of princ to output symbols. + (custom-save-face-internal): ditto. + (custom-save-resets): ditto. + +1999-08-09 Didier Verna + + * gutter-items.el (select-buffers-tab-buffers-by-mode): use + `regexp-quote' to protect the major mode name for use as a regular + expression (c++ needs this for instance). + +1999-08-08 Andy Piper + + * gutter-items.el (select-buffers-tab-buffers-by-mode): beef up to + cope with similar mode names. + + * gutter-items.el (buffers-tab-selection-function): new selection + function. + (select-buffers-tab-buffers-by-mode): new function. + (buffers-tab-items): use it if set to only display buffers in the + tab in the current buffer's group.. + (update-tab-in-gutter): use new api. + (remove-buffer-from-gutter-tab): ditto. + + * gutter-items.el (buffers-tab-max-size): set custom selection + default to 6. + (buffers-tab-switch-to-buffer): just switch window if the window is visible. + (add-tab-to-gutter): set face as default. + +1999-07-07 Jan Vroonhof + + * faces.el (frob-face-property): Merge the fall-back specifier + with the target, not replace it. + +1999-08-05 Andy Piper + + * gutter-items.el (update-tab-in-gutter): add frame argument for + buffer-items. + (update-tab-in-gutter): use it. + + * gutter-items.el (record-buffer-hook): set. + + * buffer.el (switch-to-buffer): back out switch-to-buffer-hook + change. + (switch-to-buffer-hook) deleted. + +1999-08-04 Andy Piper + + * gutter-items.el (update-tab-in-gutter): make sure this will work + as an argument to create-frame-hook. + +1999-07-30 Hrvoje Niksic + + * isearch-mode.el: Modified Bob and Darryl's code to use itimers + instead of timer emulation. + +1999-07-30 Darryl Okahata + + * isearch-mode.el: Merged Bob Glickstein's GNU + Emacs isearch enhancements. + +1999-07-28 Andy Piper + + * gutter-items.el (add-tab-to-gutter): put in specifier specs for + all devices that support tab controls. + (remove-buffer-from-gutter-tab): new function. to be used as a + value for kill-buffer-hook. + +1999-07-21 Sean MacLennan + + * auto-show.el (auto-show-truncationp): changed to match + `window_translation_on' + 1999-07-30 XEmacs Build Bot * XEmacs 21.2.19 is released @@ -27,8 +592,8 @@ 1999-07-23 Jan Vroonhof - * custom.el: - * cus-face.el: + * custom.el: + * cus-face.el: * cus-edit.el: Massive custom Theme API changes. @@ -60,7 +625,7 @@ 1999-06-25 Karl M. Hegbloom - * files.el (interpreter-mode-alist): add `make', `guile', and + * files.el (interpreter-mode-alist): add `make', `guile', and `emacs' entries. (#!/usr/bin/make -f ought to send a file into makefile-mode, guile is a scheme, and someday XEmacs will be modular enough to use as an efficient scripting tool.) @@ -244,7 +809,7 @@ * mule/mule-cmds.el (set-language-info): Don't set up menus at all. (set-language-info-alist): Set up menus here. - + 1999-06-28 MORIOKA Tomohiko * minibuf.el (completing-read): Add new optional argument diff -r 28d9c139be4c -r 11054d720c21 lisp/auto-show.el --- a/lisp/auto-show.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/auto-show.el Mon Aug 13 11:26:11 2007 +0200 @@ -92,17 +92,6 @@ :type 'number :group 'auto-show) -(defun auto-show-truncationp () - "True if line truncation is enabled for the selected window." - ;; XEmacs change (use specifiers) - ;; ### There should be a more straightforward way to do this from elisp. - (or truncate-lines - (and truncate-partial-width-windows - (< (+ (window-width) - (specifier-instance left-margin-width) - (specifier-instance right-margin-width)) - (frame-width))))) - (defun auto-show-mode (arg) "Turn automatic horizontal scroll mode on or off. With arg, turn auto scrolling on if arg is positive, off otherwise. @@ -128,7 +117,7 @@ ;; XEmacs addition: (defun auto-show-should-take-action-p () - (and auto-show-mode (auto-show-truncationp) + (and auto-show-mode (window-truncated-p) (equal (window-buffer) (current-buffer)) (not (memq this-command auto-show-inhibiting-commands)))) diff -r 28d9c139be4c -r 11054d720c21 lisp/buffer.el --- a/lisp/buffer.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/buffer.el Mon Aug 13 11:26:11 2007 +0200 @@ -32,9 +32,6 @@ ;;; Code: -(defvar switch-to-buffer-hooks nil - "Hooks to run after a recorded buffer switch.") - (defun switch-to-buffer (bufname &optional norecord) "Select buffer BUFNAME in the current window. BUFNAME may be a buffer or a buffer name and is created if it did not exist. @@ -68,8 +65,6 @@ (next-window (minibuffer-window)) (selected-window)) buf) - ;; XEmacs change - (or norecord (run-hook-with-args 'switch-to-buffer-hooks buf)) buf)) (defun pop-to-buffer (bufname &optional not-this-window-p on-frame) diff -r 28d9c139be4c -r 11054d720c21 lisp/cl-extra.el --- a/lisp/cl-extra.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/cl-extra.el Mon Aug 13 11:26:11 2007 +0200 @@ -183,16 +183,14 @@ (nreverse cl-res)))) -;; mapc is now in C, renamed from `mapc-internal'. - -;(defun mapc (cl-func cl-seq &rest cl-rest) -; "Like `mapcar', but does not accumulate values returned by the function." -; (if cl-rest -; (apply 'map nil cl-func cl-seq cl-rest) -; ;; XEmacs change: we call mapc-internal, which really doesn't -; ;; accumulate any results. -; (mapc-internal cl-func cl-seq)) -; cl-seq) +(defun mapc (cl-func cl-seq &rest cl-rest) + "Like `mapcar', but does not accumulate values returned by the function." + (if cl-rest + (apply 'map nil cl-func cl-seq cl-rest) + ;; XEmacs change: in the simplest case we call mapc-internal, + ;; which really doesn't accumulate any results. + (mapc-internal cl-func cl-seq)) + cl-seq) (defun mapl (cl-func cl-list &rest cl-rest) "Like `maplist', but does not accumulate values returned by the function." @@ -674,13 +672,13 @@ ;; The `regular' Common Lisp hash-table stuff has been moved into C. ;; Only backward compatibility stuff remains here. (defun make-hashtable (size &optional test) - (make-hash-table :size size :test test :type 'non-weak)) + (make-hash-table :test test :size size)) (defun make-weak-hashtable (size &optional test) - (make-hash-table :size size :test test :type 'weak)) + (make-hash-table :test test :size size :weakness t)) (defun make-key-weak-hashtable (size &optional test) - (make-hash-table :size size :test test :type 'key-weak)) + (make-hash-table :test test :size size :weakness 'key)) (defun make-value-weak-hashtable (size &optional test) - (make-hash-table :size size :test test :type 'value-weak)) + (make-hash-table :test test :size size :weakness 'value)) (define-obsolete-function-alias 'hashtablep 'hash-table-p) (define-obsolete-function-alias 'hashtable-fullness 'hash-table-count) @@ -693,6 +691,7 @@ (make-obsolete 'make-weak-hashtable 'make-hash-table) (make-obsolete 'make-key-weak-hashtable 'make-hash-table) (make-obsolete 'make-value-weak-hashtable 'make-hash-table) +(make-obsolete 'hash-table-type 'hash-table-weakness) (when (fboundp 'x-keysym-hash-table) (make-obsolete 'x-keysym-hashtable 'x-keysym-hash-table)) diff -r 28d9c139be4c -r 11054d720c21 lisp/cl-macs.el --- a/lisp/cl-macs.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/cl-macs.el Mon Aug 13 11:26:11 2007 +0200 @@ -1647,12 +1647,12 @@ (defsetf extent-priority set-extent-priority) (defsetf extent-property (x y &optional ignored-arg) (arg) (list 'set-extent-property x y arg)) +(defsetf extent-start-position (ext) (store) + `(progn (set-extent-endpoints ,ext ,store (extent-end-position ,ext)) + ,store)) (defsetf extent-end-position (ext) (store) - (list 'progn (list 'set-extent-endpoints (list 'extent-start-position ext) - store) store)) -(defsetf extent-start-position (ext) (store) - (list 'progn (list 'set-extent-endpoints store - (list 'extent-end-position ext)) store)) + `(progn (set-extent-endpoints ,ext (extent-start-position ,ext) ,store) + ,store)) (defsetf face-background (f &optional s) (x) (list 'set-face-background f x s)) (defsetf face-background-pixmap (f &optional s) (x) (list 'set-face-background-pixmap f x s)) diff -r 28d9c139be4c -r 11054d720c21 lisp/cl.el --- a/lisp/cl.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/cl.el Mon Aug 13 11:26:11 2007 +0200 @@ -680,9 +680,9 @@ ;(load "cl-defs") ;;; Define data for indentation and edebug. -(mapc +(mapcar #'(lambda (entry) - (mapc + (mapcar #'(lambda (func) (put func 'lisp-indent-function (nth 1 entry)) (put func 'lisp-indent-hook (nth 1 entry)) diff -r 28d9c139be4c -r 11054d720c21 lisp/cmdloop.el --- a/lisp/cmdloop.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/cmdloop.el Mon Aug 13 11:26:11 2007 +0200 @@ -319,23 +319,36 @@ (if (and teach-extended-commands-p (interactive-p)) - ;; We need to fiddle with keys: remember the keys, run the - ;; command, and show the keys (if any). + ;; Remember the keys, run the command, and show the keys (if + ;; any). The funny variable names are a poor man's guarantee + ;; that we don't get tripped by this-command doing something + ;; funny. Quoth our forefathers: "We want lexical scope!" (let ((_execute_command_keys_ (where-is-internal this-command)) (_execute_command_name_ this-command)) ; the name can change (command-execute this-command t) - (when (and _execute_command_keys_ - ;; Wait for a while, so the user can see a message - ;; printed, if any. - (sit-for 1)) - (display-message - 'no-log - (format "Command `%s' is bound to key%s: %s" - _execute_command_name_ - (if (cdr _execute_command_keys_) "s" "") - (sorted-key-descriptions _execute_command_keys_))) - (sit-for teach-extended-commands-timeout) - (clear-message 'no-log))) + (when _execute_command_keys_ + ;; Normally the region is adjusted in post_command_hook; + ;; however, it is not called until after we finish. It + ;; looks ugly for the region to get updated after the + ;; delays, so we do it now. The code below is a Lispified + ;; copy of code in event-stream.c:post_command_hook(). + (if (and (not zmacs-region-stays) + (or (not (eq (selected-window) (minibuffer-window))) + (eq (zmacs-region-buffer) (current-buffer)))) + (zmacs-deactivate-region) + (zmacs-update-region)) + ;; Wait for a while, so the user can see a message printed, + ;; if any. + (when (sit-for 1) + (display-message + 'no-log + (format (if (cdr _execute_command_keys_) + "Command `%s' is bound to keys: %s" + "Command `%s' is bound to key: %s") + _execute_command_name_ + (sorted-key-descriptions _execute_command_keys_))) + (sit-for teach-extended-commands-timeout) + (clear-message 'no-log)))) ;; Else, just run the command. (command-execute this-command t))) diff -r 28d9c139be4c -r 11054d720c21 lisp/code-process.el --- a/lisp/code-process.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/code-process.el Mon Aug 13 11:26:11 2007 +0200 @@ -198,9 +198,9 @@ See also the function `find-operation-coding-system'.") -(defun open-network-stream (name buffer host service) +(defun open-network-stream (name buffer host service &optional protocol) "Open a TCP connection for a service to a host. -Returns a subprocess-object to represent the connection. +Return a subprocess-object to represent the connection. Input and output work as for subprocesses; `delete-process' closes it. Args are NAME BUFFER HOST SERVICE. NAME is name for process. It is modified if necessary to make it unique. @@ -211,7 +211,17 @@ with any buffer Third arg is name of the host to connect to, or its IP address. Fourth arg SERVICE is name of the service desired, or an integer - specifying a port number to connect to." + specifying a port number to connect to. +Fifth argument PROTOCOL is a network protocol. Currently 'tcp + (Transmission Control Protocol) and 'udp (User Datagram Protocol) are + supported. When omitted, 'tcp is assumed. + +Ouput via `process-send-string' and input via buffer or filter (see +`set-process-filter') are stream-oriented. That means UDP datagrams are +not guaranteed to be sent and received in discrete packets. (But small +datagrams around 500 bytes that are not truncated by `process-send-string' +are usually fine.) Note further that UDP protocol does not guard against +lost packets." (let (cs-r cs-w) (let (ret) (catch 'found @@ -245,6 +255,6 @@ (or coding-system-for-read cs-r)) (coding-system-for-write (or coding-system-for-write cs-w))) - (open-network-stream-internal name buffer host service)))) + (open-network-stream-internal name buffer host service protocol)))) ;;; mule-process.el ends here diff -r 28d9c139be4c -r 11054d720c21 lisp/cus-edit.el --- a/lisp/cus-edit.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/cus-edit.el Mon Aug 13 11:26:11 2007 +0200 @@ -3280,7 +3280,7 @@ (when (or (and spec (eq (car spec) 'user) (eq (second spec) 'set)) comment) (princ "\n '(") - (princ symbol) + (prin1 symbol) (princ " ") ;; This comment stuf is in the way #### ;; Is (eq (third spec) (car saved-value)) ???? @@ -3313,7 +3313,7 @@ (eq (car theme-spec) 'user) (eq (second theme-spec) 'set)) comment) (princ "\n '(") - (princ symbol) + (prin1 symbol) (princ " ") (prin1 (get symbol 'saved-face)) (if (or comment now) @@ -3358,7 +3358,7 @@ (princ "(") (princ (quote ,setter)) (princ "\n '(") - (princ object) + (prin1 object) (princ " ") (prin1 (third spec)) (princ ")"))))))) diff -r 28d9c139be4c -r 11054d720c21 lisp/cus-start.el --- a/lisp/cus-start.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/cus-start.el Mon Aug 13 11:26:11 2007 +0200 @@ -63,6 +63,7 @@ ;; integer (auto-save-interval auto-save integer) (bell-volume sound integer) + (bell-inhibit-time sound integer) (echo-keystrokes keyboard integer) (gc-cons-threshold alloc integer) (next-screen-context-lines display integer) diff -r 28d9c139be4c -r 11054d720c21 lisp/dump-paths.el --- a/lisp/dump-paths.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/dump-paths.el Mon Aug 13 11:26:11 2007 +0200 @@ -39,7 +39,12 @@ (princ (format "XEmacs thinks the roots of its hierarchy are:\n%S\n" roots))) - (let ((stuff (packages-find-packages roots))) + (let* ((package-locations + (packages-compute-package-locations + ;; temporary kludge: + ;; this should be synched with startup.el + (paths-construct-path '("~" ".xemacs")))) + (stuff (packages-find-packages roots package-locations))) (setq late-packages (car (cdr stuff)))) (setq late-package-load-path (packages-find-package-load-path late-packages)) diff -r 28d9c139be4c -r 11054d720c21 lisp/faces.el --- a/lisp/faces.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/faces.el Mon Aug 13 11:26:11 2007 +0200 @@ -834,12 +834,12 @@ ;; happen if that locale has no instantiators. So signal ;; an error to indicate this. - (setq temp-sp - (if (and (or (eq locale 'global) (eq locale 'all) (not locale)) - (not (face-property face property 'global))) - (copy-specifier (face-property 'default property) - nil 'global) - sp)) + + (setq temp-sp (copy-specifier sp)) + (if (and (or (eq locale 'global) (eq locale 'all) (not locale)) + (not (face-property face property 'global))) + (copy-specifier (face-property 'default property) + temp-sp 'global)) (if (and (valid-specifier-locale-p locale) (not (specifier-specs temp-sp locale))) (error "Property must have a specification in locale %S" locale)) @@ -1410,7 +1410,8 @@ (mswindows-init-device-faces device)) ;; Nothing to do for TTYs? ) - (init-other-random-faces device))) + (or (eq 'stream (device-type device)) + (init-other-random-faces device)))) (defun init-frame-faces (frame) (when init-face-from-resources @@ -1618,6 +1619,7 @@ (set-face-underline-p 'underline t 'global '(default))) (make-face 'zmacs-region "Used on highlightes region between point and mark.") (make-face 'isearch "Used on region matched by isearch.") +(make-face 'isearch-secondary "Face to use for highlighting all matches.") (make-face 'list-mode-item-selected "Face for the selected list item in list-mode.") (make-face 'highlight "Highlight face.") @@ -1707,6 +1709,13 @@ ((mswindows default color) . "green")) 'global) +;; #### This should really, I mean *really*, be converted to some form +;; of `defface' one day. +(set-face-foreground 'isearch-secondary + '(((x default color) . "red3") + ((mswindows default color) . "red3")) + 'global) + ;; Define some logical color names to be used when reading the pixmap files. (if (featurep 'xpm) (setq xpm-color-symbols diff -r 28d9c139be4c -r 11054d720c21 lisp/files.el --- a/lisp/files.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/files.el Mon Aug 13 11:26:11 2007 +0200 @@ -1272,7 +1272,7 @@ from the end of the file name anything that matches one of these regexps.") (defvar user-init-file - "" ; set by command-line + nil ; set by command-line "File name including directory of user's initialization file.") (defun set-auto-mode (&optional just-from-file-name) @@ -2753,11 +2753,12 @@ (not (file-exists-p file-name))) (error "Auto-save file %s not current" file-name)) ((save-window-excursion - (with-output-to-temp-buffer "*Directory*" - (buffer-disable-undo standard-output) - (call-process "ls" nil standard-output nil - (if (file-symlink-p file) "-lL" "-l") - file file-name)) + (if (not (eq system-type 'windows-nt)) + (with-output-to-temp-buffer "*Directory*" + (buffer-disable-undo standard-output) + (call-process "ls" nil standard-output nil + (if (file-symlink-p file) "-lL" "-l") + file file-name))) (yes-or-no-p (format "Recover auto save file %s? " file-name))) (switch-to-buffer (find-file-noselect file t)) (let ((buffer-read-only nil)) diff -r 28d9c139be4c -r 11054d720c21 lisp/find-paths.el --- a/lisp/find-paths.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/find-paths.el Mon Aug 13 11:26:11 2007 +0200 @@ -218,13 +218,13 @@ ;; from more to less specific (paths-find-version-directory roots (concat base system-configuration) - envvar) + envvar default) (paths-find-version-directory roots base envvar) (paths-find-version-directory roots system-configuration - envvar default))) + envvar))) (defun construct-emacs-version-name () "Construct the raw XEmacs version number." diff -r 28d9c139be4c -r 11054d720c21 lisp/font-lock.el --- a/lisp/font-lock.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/font-lock.el Mon Aug 13 11:26:11 2007 +0200 @@ -2444,11 +2444,11 @@ (goto-char (match-end 1)) (goto-char (match-end 0)) (1 font-lock-variable-name-face)))))) - + ;; Modifier keywords and Java doc tags (setq java-font-lock-keywords-3 (append - + '( ;; Feature scoping: ;; These must come first or the Modifiers from keywords-1 will @@ -2458,11 +2458,11 @@ ("\\" 0 font-lock-preprocessor-face) ("\\" 0 font-lock-reference-face)) java-font-lock-keywords-2 - + (list ;; Java doc tags - '("@\\(author\\|exception\\|param\\|return\\|see\\|version\\)\\s " + '("@\\(author\\|exception\\|throws\\|deprecated\\|param\\|return\\|see\\|since\\|version\\)\\s " 0 font-lock-keyword-face t) ;; Doc tag - Parameter identifiers @@ -2470,7 +2470,17 @@ 1 'font-lock-variable-name-face t) ;; Doc tag - Exception types - (list (concat "@exception\\ s*" + (list (concat "@exception\\s +" + java-font-lock-identifier-regexp) + '(1 (if (equal (char-after (match-end 0)) ?.) + font-lock-reference-face font-lock-type-face) t) + (list (concat "\\=\\." java-font-lock-identifier-regexp) + '(goto-char (match-end 0)) nil + '(1 (if (equal (char-after (match-end 0)) ?.) + 'font-lock-reference-face 'font-lock-type-face) t))) + + ;; Doc tag - Exception types + (list (concat "@exception\\s +" java-font-lock-identifier-regexp) '(1 (if (equal (char-after (match-end 0)) ?.) font-lock-reference-face font-lock-type-face) t) @@ -2482,7 +2492,14 @@ ;; Doc tag - Cross-references, usually to methods '("@see\\s +\\(\\S *[^][ \t\n\r\f(){},.;:]\\)" 1 font-lock-function-name-face t) - + + ;; Doc tag - Links + '("{@link\\s +\\([^}]*\\)}" + 0 font-lock-keyword-face t) + ;; Doc tag - Links + '("{@link\\s +\\(\\S +\\s +\\S +\\)}" + 1 font-lock-function-name-face t) + ))) ) diff -r 28d9c139be4c -r 11054d720c21 lisp/gnuserv.el --- a/lisp/gnuserv.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/gnuserv.el Mon Aug 13 11:26:11 2007 +0200 @@ -440,6 +440,7 @@ (client (make-gnuclient :id gnuserv-current-client :device device :frame new-frame))) + (select-frame frame) (setq gnuserv-current-client nil) ;; If the device was created by this client, push it to the list. (and (/= old-device-num (length (device-list))) diff -r 28d9c139be4c -r 11054d720c21 lisp/gui.el --- a/lisp/gui.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/gui.el Mon Aug 13 11:26:11 2007 +0200 @@ -83,7 +83,7 @@ "True if OBJECT is a GUI button." (and (vectorp object) (> (length object) 0) - (eq 'gui-button (aref object 0)))) + (eq 'button (aref object 0)))) (make-face 'gui-button-face "Face used for gui buttons") (if (not (face-differs-from-default-p 'gui-button-face)) @@ -98,26 +98,15 @@ "Make a GUI button whose label is STRING and whose action is ACTION. If the button is inserted in a buffer and then clicked on, and ACTION is non-nil, ACTION will be called with one argument, USER-DATA." - (vector 'gui-button - (if (featurep 'xpm) - (xpm-button-create - string gui-button-shadow-thickness - (color-instance-name (face-foreground-instance 'gui-button-face)) - (color-instance-name (face-background-instance 'gui-button-face))) - (xbm-button-create string gui-button-shadow-thickness)) - action user-data)) + (vector 'button + :descriptor string + :face 'gui-button-face + :callback `(funcall (quote ,action) (quote ,user-data)))) (defun insert-gui-button (button &optional pos buffer) "Insert GUI button BUTTON at POS in BUFFER." (check-argument-type 'gui-button-p button) - (let ((annotation - (make-annotation (make-glyph (car (aref button 1))) - pos 'text buffer nil - (make-glyph (cadr (aref button 1))))) - (action (aref button 2))) - (and action - (progn - (set-annotation-action annotation action) - (set-annotation-data annotation (aref button 3)))))) + (make-annotation (make-glyph button) + pos 'text buffer nil)) ;;; gui.el ends here diff -r 28d9c139be4c -r 11054d720c21 lisp/gutter-items.el --- a/lisp/gutter-items.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/gutter-items.el Mon Aug 13 11:26:11 2007 +0200 @@ -70,7 +70,7 @@ shown. If this is nil, then all buffers will be shown. Setting this to a large number or nil will slow down tab responsiveness." :type '(choice (const :tag "Show all" nil) - (integer 10)) + (integer 6)) :group 'buffers-tab) (defcustom buffers-tab-switch-to-buffer-function 'buffers-tab-switch-to-buffer @@ -91,18 +91,102 @@ function) :group 'buffers-tab) -(defcustom buffers-tab-format-buffer-line-function 'format-buffers-menu-line +(defcustom buffers-tab-selection-function 'select-buffers-tab-buffers-by-mode + "*If non-nil, a function specifying the buffers to select from the +buffers tab. This is passed two buffers and should return non-nil if +the second buffer should be selected. The default value +`select-buffers-tab-buffers-by-mode' groups buffers by major mode and +by `buffers-tab-grouping-regexp'." + + :type '(choice (const :tag "None" nil) + function) + :group 'buffers-tab) + +(defcustom buffers-tab-face 'default + "*Face to use for displaying the buffers tab." + :type 'face + :group 'buffers-tab) + +(defcustom buffers-tab-grouping-regexp + '("^\\(gnus-\\|message-mode\\|mime/viewer-mode\\)" + "^\\(emacs-lisp-\\|lisp-\\)") + "*If non-nil, a list of regular expressions for buffer grouping. +Each regular expression is applied to the current major-mode symbol +name and mode-name, if it matches then any other buffers that match +the same regular expression be added to the current group." + :type '(choice (const :tag "None" nil) + sexp) + :group 'buffers-tab) + +(defcustom buffers-tab-format-buffer-line-function 'format-buffers-tab-line "*The function to call to return a string to represent a buffer in the -buffers tab. The function is passed a buffer and should return a string. -The default value `format-buffers-menu-line' just returns the name of -the buffer. Also check out `slow-format-buffers-menu-line' which -returns a whole bunch of info about a buffer." +buffers tab. The function is passed a buffer and should return a +string. The default value `format-buffers-tab-line' just returns the +name of the buffer, optionally truncated to +`buffers-tab-max-buffer-line-length'. Also check out +`slow-format-buffers-menu-line' which returns a whole bunch of info +about a buffer." :type 'function :group 'buffers-tab) +(defvar buffers-tab-default-buffer-line-length + (make-specifier-and-init 'generic '((global ((default) . 25))) t) + "*Maximum length of text which may appear in a \"Buffers\" tab. +This is a specifier, use set-specifier to modify it.") + +(defcustom buffers-tab-max-buffer-line-length + (specifier-instance buffers-tab-default-buffer-line-length) + "*Maximum length of text which may appear in a \"Buffers\" tab. +Buffer names over this length will be truncated with elipses. +If this is 0, then the full buffer name will be shown." + :type '(choice (const :tag "Show all" 0) + (integer 25)) + :group 'buffers-tab + :set #'(lambda (var val) + (set-specifier buffers-tab-default-buffer-line-length val) + (setq buffers-tab-max-buffer-line-length val))) + (defun buffers-tab-switch-to-buffer (buffer) "For use as a value for `buffers-tab-switch-to-buffer-function'." - (switch-to-buffer buffer t)) + (unless (eq (window-buffer) buffer) + (if (> (length (windows-of-buffer buffer)) 0) + (select-window (car (windows-of-buffer buffer))) + (switch-to-buffer buffer t)))) + +(defun select-buffers-tab-buffers-by-mode (buf1 buf2) + "For use as a value of `buffers-tab-selection-function'. +This selects buffers by major mode `buffers-tab-grouping-regexp'." + (let ((mode1 (symbol-name (symbol-value-in-buffer 'major-mode buf1))) + (mode2 (symbol-name (symbol-value-in-buffer 'major-mode buf2))) + (modenm1 (symbol-value-in-buffer 'mode-name buf1)) + (modenm2 (symbol-value-in-buffer 'mode-name buf2))) + (cond ((or (eq mode1 mode2) + (eq modenm1 modenm2) + (and (string-match "^[^-]+-" mode1) + (string-match + (concat "^" (regexp-quote + (substring mode1 0 (match-end 0)))) + mode2)) + (and buffers-tab-grouping-regexp + (find-if #'(lambda (x) + (or + (and (string-match x mode1) + (string-match x mode2)) + (and (string-match x modenm1) + (string-match x modenm2)))) + buffers-tab-grouping-regexp))) + t) + (t nil)))) + +(defun format-buffers-tab-line (buffer) + "For use as a value of `buffers-tab-format-buffer-line-function'. +This just returns the buffer's name, optionally truncated." + (let ((len (specifier-instance buffers-tab-default-buffer-line-length))) + (if (and (> len 0) + (> (length (buffer-name buffer)) len)) + (concat (substring (buffer-name buffer) + 0 (- len 3)) "...") + (buffer-name buffer)))) (defsubst build-buffers-tab-internal (buffers) (let (line) @@ -114,14 +198,24 @@ (buffer-name buffer)))) buffers))) -(defun buffers-tab-items () +(defun buffers-tab-items (&optional in-deletion frame) "This is the tab filter for the top-level buffers \"Buffers\" tab. It dynamically creates a list of buffers to use as the contents of the tab. Only the most-recently-used few buffers will be listed on the tab, for efficiency reasons. You can control how many buffers will be shown by setting `buffers-tab-max-size'. You can control the text of the tab items by redefining the function `format-buffers-menu-line'." - (let ((buffers (delete-if buffers-tab-omit-function (buffer-list)))) + (let* ((buffers (delete-if buffers-tab-omit-function (buffer-list frame))) + (first-buf (car buffers))) + ;; if we're in deletion ignore the current buffer + (when in-deletion + (setq buffers (delq (current-buffer) buffers)) + (setq first-buf (car buffers))) + ;; group buffers by mode + (when buffers-tab-selection-function + (delete-if-not #'(lambda (buf) + (funcall buffers-tab-selection-function + first-buf buf)) buffers)) (and (integerp buffers-tab-max-size) (> buffers-tab-max-size 1) (> (length buffers) buffers-tab-max-size) @@ -137,24 +231,308 @@ (make-extent 0 0 gutter-string) (setq gutter-buffers-tab (make-glyph - (vector 'tab-control :descriptor "Buffers" + (vector 'tab-control :descriptor "Buffers" :face buffers-tab-face :properties (list :items (buffers-tab-items)))))) ;; This looks better than a 3d border - (set-specifier default-gutter-border-width 0 'global 'mswindows) - (set-specifier default-gutter gutter-string 'global 'mswindows))) + (mapcar '(lambda (x) + (when (valid-image-instantiator-format-p 'tab-control x) + (set-specifier default-gutter-border-width 0 'global x) + (set-specifier default-gutter gutter-string 'global x))) + (console-type-list)))) -(defun update-tab-in-gutter (&optional notused) +(defun update-tab-in-gutter (&optional frame-or-buffer) "Update the tab control in the gutter area." - (when (valid-image-instantiator-format-p 'tab-control) - (set-image-instance-property (glyph-image-instance gutter-buffers-tab) - :items - (buffers-tab-items)) - (resize-subwindow (glyph-image-instance gutter-buffers-tab) - (gutter-pixel-width) nil))) + (let ((locale (if (framep frame-or-buffer) frame-or-buffer))) + (when (specifier-instance default-gutter-visible-p locale) + (unless gutter-buffers-tab + (add-tab-to-gutter)) + (when (valid-image-instantiator-format-p 'tab-control) + (let ((inst (glyph-image-instance + gutter-buffers-tab + (when (framep frame-or-buffer) + (last-nonminibuf-window frame-or-buffer))))) + (set-image-instance-property inst :items + (buffers-tab-items + nil locale)) + (resize-subwindow inst (gutter-pixel-width) nil)) + )))) + +(defun remove-buffer-from-gutter-tab () + "Remove the current buffer from the tab control in the gutter area." + (when (and (valid-image-instantiator-format-p 'tab-control) + (specifier-instance default-gutter-visible-p)) + (let ((inst (glyph-image-instance gutter-buffers-tab)) + (buffers (buffers-tab-items t))) + (unless buffers + (setq buffers (build-buffers-tab-internal + (list + (get-buffer-create "*scratch*"))))) + (set-image-instance-property inst :items buffers) + (resize-subwindow inst (gutter-pixel-width) nil) + ))) + +(add-hook 'kill-buffer-hook 'remove-buffer-from-gutter-tab) +(add-hook 'create-frame-hook 'update-tab-in-gutter) +(add-hook 'record-buffer-hook 'update-tab-in-gutter) + +;; +;; progress display +;; ripped off from message display +;; +(defvar progress-stack nil + "An alist of label/string pairs representing active progress gauges. +The first element in the list is currently displayed in the gutter area. +Do not modify this directly--use the `progress' or +`display-progress'/`clear-progress' functions.") + +(defvar progress-glyph-height 32 + "Height of the gutter area for progress messages.") + +(defvar progress-stop-callback 'progress-quit-function + "Function to call to stop the progress operation.") + +(defun progress-quit-function () + "Default function to call for the stop button in a progress gauge. +This just removes the progress gauge and calls quit." + (interactive) + (clear-progress) + (keyboard-quit)) + +;; private variables +(defvar progress-gauge-glyph + (make-glyph + (vector 'progress-gauge + :pixel-height (- progress-glyph-height 8) + :pixel-width 250 + :descriptor "Progress"))) + +(defvar progress-text-glyph + (make-glyph [string :data ""])) + +(defvar progress-layout-glyph + (make-glyph + (vector + 'layout :orientation 'vertical :justify 'left + :items (list + progress-text-glyph + (make-glyph + (vector + 'layout :pixel-height progress-glyph-height + :orientation 'horizontal + :items (list + progress-gauge-glyph + (vector + 'button :pixel-height (- progress-glyph-height 8) + :descriptor " Stop " + :callback '(funcall progress-stop-callback))))))))) + +(defvar progress-abort-glyph + (make-glyph + (vector 'layout :orientation 'vertical :justify 'left + :items (list progress-text-glyph + (make-glyph + (vector 'layout + :pixel-height progress-glyph-height + :orientation 'horizontal)))))) + +(defvar progress-extent-text "") +(defvar progress-extent nil) + +(defun progress-displayed-p (&optional return-string frame) + "Return a non-nil value if a progress gauge is presently displayed in the +gutter area. If optional argument RETURN-STRING is non-nil, +return a string containing the message, otherwise just return t." + (let ((buffer (get-buffer-create " *Gutter Area*"))) + (and (< (point-min buffer) (point-max buffer)) + (if return-string + (buffer-substring nil nil buffer) + t)))) + +;;; Returns the string which remains in the echo area, or nil if none. +;;; If label is nil, the whole message stack is cleared. +(defun clear-progress (&optional label frame no-restore) + "Remove any progress gauge with the given LABEL from the progress gauge-stack, +erasing it from the gutter area if it's currently displayed there. +If a message remains at the head of the progress-stack and NO-RESTORE +is nil, it will be displayed. The string which remains in the gutter +area will be returned, or nil if the progress-stack is now empty. +If LABEL is nil, the entire progress-stack is cleared. + +Unless you need the return value or you need to specify a label, +you should just use (progress nil)." + (or frame (setq frame (selected-frame))) + (remove-progress label frame) + (let ((inhibit-read-only t) + (zmacs-region-stays zmacs-region-stays)) ; preserve from change + (erase-buffer " *Echo Area*") + (erase-buffer (get-buffer-create " *Gutter Area*"))) + (if no-restore + nil ; just preparing to put another msg up + (if progress-stack + (let ((oldmsg (cdr (car progress-stack)))) + (raw-append-progress oldmsg frame) + oldmsg) + ;; nothing to display so get rid of the gauge + (set-specifier bottom-gutter-border-width 0 frame) + (set-specifier bottom-gutter-visible-p nil frame)))) -(add-tab-to-gutter) -(add-hook 'switch-to-buffer-hooks 'update-tab-in-gutter) -(add-hook 'create-frame-hook 'update-tab-in-gutter) +(defun remove-progress (&optional label frame) + ;; If label is nil, we want to remove all matching progress gauges. + (while (and progress-stack + (or (null label) ; null label means clear whole stack + (eq label (car (car progress-stack))))) + (setq progress-stack (cdr progress-stack))) + (let ((s progress-stack)) + (while (cdr s) + (let ((msg (car (cdr s)))) + (if (eq label (car msg)) + (progn + (setcdr s (cdr (cdr s)))) + (setq s (cdr s))))))) + +(defun append-progress (label message &optional value frame) + (or frame (setq frame (selected-frame))) + ;; Add a new entry to the message-stack, or modify an existing one + (let* ((top (car progress-stack)) + (tmsg (cdr top))) + (if (eq label (car top)) + (progn + (setcdr top message) + (if (eq tmsg message) + (set-image-instance-property + (glyph-image-instance progress-gauge-glyph) + :percent value) + (raw-append-progress message value frame)) + (redisplay-gutter-area) + (when (input-pending-p) + (dispatch-event (next-command-event)))) + (push (cons label message) progress-stack) + (raw-append-progress message value frame)) + (when (eq value 100) + (sit-for 0.5 nil) + (clear-progress label)))) + +(defun abort-progress (label message &optional frame) + (or frame (setq frame (selected-frame))) + ;; Add a new entry to the message-stack, or modify an existing one + (let* ((top (car progress-stack)) + (inhibit-read-only t) + (zmacs-region-stays zmacs-region-stays)) + (if (eq label (car top)) + (setcdr top message) + (push (cons label message) progress-stack)) + (unless (equal message "") + (insert-string message (get-buffer-create " *Gutter Area*")) + ;; Do what the device is able to cope with. + (if (not (valid-image-instantiator-format-p 'progress-gauge frame)) + (progn + (insert-string message " *Echo Area*") + (if (not executing-kbd-macro) + (redisplay-echo-area))) + ;; do some funky display here. + (unless progress-extent + (setq progress-extent (make-extent 0 0 progress-extent-text))) + (let ((bglyph (extent-begin-glyph progress-extent))) + (set-extent-begin-glyph progress-extent progress-abort-glyph) + ;; fixup the gutter specifiers + (set-specifier bottom-gutter progress-extent-text frame) + (set-specifier bottom-gutter-border-width 2 frame) + (set-image-instance-property + (glyph-image-instance progress-text-glyph) :data message) + (set-specifier bottom-gutter-height 'autodetect frame) + (set-specifier bottom-gutter-visible-p t frame) + ;; we have to do this so redisplay is up-to-date and so + ;; redisplay-gutter-area performs optimally. + (redisplay-gutter-area) + (sit-for 0.5 nil) + (clear-progress label) + (set-extent-begin-glyph progress-extent bglyph) + ))))) + +(defun raw-append-progress (message &optional value frame) + (unless (equal message "") + (let ((inhibit-read-only t) + (zmacs-region-stays zmacs-region-stays) + (val (or value 0))) ; preserve from change + (insert-string message (get-buffer-create " *Gutter Area*")) + ;; Do what the device is able to cope with. + (if (not (valid-image-instantiator-format-p 'progress-gauge frame)) + (progn + (insert-string + (concat message (if (eq val 100) "done.") + (make-string (/ val 5) ?.)) + " *Echo Area*") + (if (not executing-kbd-macro) + (redisplay-echo-area))) + ;; do some funky display here. + (unless progress-extent + (setq progress-extent (make-extent 0 0 progress-extent-text)) + (set-extent-begin-glyph progress-extent progress-layout-glyph)) + ;; fixup the gutter specifiers + (set-specifier bottom-gutter progress-extent-text frame) + (set-specifier bottom-gutter-border-width 2 frame) + (set-image-instance-property + (glyph-image-instance progress-gauge-glyph) :percent val) + (set-image-instance-property + (glyph-image-instance progress-text-glyph) :data message) + (if (and (eq (specifier-instance bottom-gutter-height frame) + 'autodetect) + (specifier-instance bottom-gutter-visible-p frame)) + (progn + ;; if the gauge is already visible then just draw the gutter + ;; checking for user events + (redisplay-gutter-area) + (when (input-pending-p) + (dispatch-event (next-command-event)))) + ;; otherwise make the gutter visible and redraw the frame + (set-specifier bottom-gutter-height 'autodetect frame) + (set-specifier bottom-gutter-visible-p t frame) + ;; we have to do this so redisplay is up-to-date and so + ;; redisplay-gutter-area performs optimally. + (redisplay-frame) + ))))) + +(defun display-progress (label message &optional value frame) + "Display a progress gauge and message in the bottom gutter area. + First argument LABEL is an identifier for this message. MESSAGE is +the string to display. Use `clear-progress' to remove a labelled +message." + (clear-progress label frame t) + (if (eq value 'abort) + (abort-progress label message frame) + (append-progress label message value frame))) + +(defun current-progress (&optional frame) + "Return the current progress gauge in the gutter area, or nil. +The FRAME argument is currently unused." + (cdr (car progress-stack))) + +;;; may eventually be frame-dependent +(defun current-progress-label (&optional frame) + (car (car progress-stack))) + +(defun progress (fmt &optional value &rest args) + "Print a progress gauge and message in the bottom gutter area of the frame. +The arguments are the same as to `format'. + +If the only argument is nil, clear any existing progress gauge." + (if (and (null fmt) (null args)) + (prog1 nil + (clear-progress nil)) + (let ((str (apply 'format fmt args))) + (display-progress 'progress str value) + str))) + +(defun lprogress (label fmt &optional value &rest args) + "Print a progress gauge and message in the bottom gutter area of the frame. +First argument LABEL is an identifier for this progress gauge. The rest of the +arguments are the same as to `format'." + (if (and (null fmt) (null args)) + (prog1 nil + (clear-progress label nil)) + (let ((str (apply 'format fmt args))) + (display-progress label str value) + str))) (provide 'gutter-items) ;;; gutter-items.el ends here. diff -r 28d9c139be4c -r 11054d720c21 lisp/indent.el --- a/lisp/indent.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/indent.el Mon Aug 13 11:26:11 2007 +0200 @@ -93,7 +93,7 @@ (back-to-indentation) (let ((cur-col (current-column))) (cond ((< cur-col column) - (if (> (- column (* (/ cur-col tab-width) tab-width)) tab-width) + (if (>= (- column (* (/ cur-col tab-width) tab-width)) tab-width) (delete-region (point) (progn (skip-chars-backward " ") (point)))) (indent-to column)) diff -r 28d9c139be4c -r 11054d720c21 lisp/info.el --- a/lisp/info.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/info.el Mon Aug 13 11:26:11 2007 +0200 @@ -459,6 +459,7 @@ ;; Is this right for NT? .zip, with -c for to stdout, right? (defvar Info-suffix-list '( ("" . nil) (".info" . nil) + (".info.bz2" . "bzip2 -dc %s") (".info.gz" . "gzip -dc %s") (".info-z" . "gzip -dc %s") (".info.Z" . "uncompress -c %s") @@ -501,9 +502,12 @@ "List of possible matches for last Info-index command.") (defvar Info-index-first-alternative nil) -(defcustom Info-annotations-path '("~/.xemacs/info.notes" - "~/.infonotes" - "/usr/lib/info.notes") +(defcustom Info-annotations-path + (list + (paths-construct-path (list user-init-directory "info.notes")) + (paths-construct-path '("~" ".infonotes")) + (paths-construct-path '("usr" "lib" "info.notes") + (char-to-string directory-sep-char))) "*Names of files that contain annotations for different Info nodes. By convention, the first one should reside in your personal directory. The last should be a world-writable \"public\" annotations file." @@ -2060,11 +2064,9 @@ (progn (Info-global-prev) (message "Node: %s" Info-current-node) - (sit-for 0) - ;;(scroll-up 1) ; work around bug in pos-visible-in-window-p - ;;(scroll-down 1) - (while (not (pos-visible-in-window-p (point-max))) - (scroll-up))) + (goto-char (point-max)) + (recenter -1) + (move-to-window-line 0)) (scroll-down))))) (defun Info-scroll-prev (arg) diff -r 28d9c139be4c -r 11054d720c21 lisp/isearch-mode.el --- a/lisp/isearch-mode.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/isearch-mode.el Mon Aug 13 11:26:11 2007 +0200 @@ -1,6 +1,6 @@ ;;; isearch-mode.el --- Incremental search minor mode. -;; Copyright (C) 1992, 1993, 1997 Free Software Foundation, Inc. +;; Copyright (C) 1992,93,94,95,96,97,98,1999 Free Software Foundation, Inc. ;; Author: Daniel LaLiberte ;; Maintainer: XEmacs Development Team @@ -19,35 +19,29 @@ ;; General Public License for more details. ;; You should have received a copy of the GNU General Public License -;; along with XEmacs; see the file COPYING. If not, write to the +;; along with XEmacs; see the file COPYING. If not, write to the ;; Free Software Foundation, 59 Temple Place - Suite 330, ;; Boston, MA 02111-1307, USA. -;;; Synched up with: Not synched with FSF. +;;; Synched up with: FSF 20.4. ;;; Commentary: -;; LCD Archive Entry: -;; isearch-mode|Daniel LaLiberte|liberte@cs.uiuc.edu -;; |A minor mode replacement for isearch.el. - -;;==================================================================== ;; Instructions -;; Searching with isearch-mode.el should work just like isearch.el, -;; except it is done in a temporary minor mode that terminates when -;; you finish searching. +;; Searching with isearch-mode.el should work just like isearch.el +;; [the one from Emacs 18], except it is done in a temporary minor +;; mode that terminates when you finish searching. -;; Semi-modal searching is supported, using a recursive edit. If -;; isearching is started non-interactively by calling one of the -;; isearch commands (e.g. (isearch-forward), but not like gnus does -;; it: (call-interactively 'isearch-forward)), isearch-mode does not -;; return until the search is completed. You should still be able -;; switch buffers, so be careful not to get things confused. +;; For programmed use of isearch-mode, e.g. calling (isearch-forward), +;; isearch-mode behaves modally and does not return until the search +;; is completed. It uses a recursive-edit to behave this way. In +;; that case, you should still be able switch buffers, so be careful +;; not to get things confused. ;; The key bindings active within isearch-mode are defined below in ;; `isearch-mode-map' which is given bindings close to the default -;; characters of isearch.el for version 19. With `isearch-mode', +;; characters of the original isearch.el. With `isearch-mode', ;; however, you can bind multi-character keys and it should be easier ;; to add new commands. One bug though: keys with meta-prefix cannot ;; be longer than two chars. Also see minibuffer-local-isearch-map @@ -63,16 +57,18 @@ ;; Exiting immediately from isearch uses isearch-edit-string instead ;; of nonincremental-search, if search-nonincremental-instead is non-nil. ;; The name of this option should probably be changed if we decide to -;; keep the behavior. One difference is that isearch-edit-string does -;; not support word search yet; perhaps isearch-mode should support it -;; even for incremental searches, but how? +;; keep the behavior. No point in forcing nonincremental search until +;; the last possible moment. -;;==================================================================== -;;; Change History: +;; TODO +;; - Integrate generalized command history to isearch-edit-string. +;; - Think about incorporating query-replace. +;; - Hooks and options for failed search. -;; Header: /import/kaplan/kaplan/liberte/Isearch/RCS/isearch-mode.el,v 1.3 92/06/29 13:10:08 liberte Exp Locker: liberte -;; Log: isearch-mode.el,v -;; +;;; Change Log: + +;; Changes before those recorded in ChangeLog: + ;; 20-aug-92 Hacked by jwz for Lucid Emacs 19.3. ;; ;; Revision 1.3 92/06/29 13:10:08 liberte @@ -83,7 +79,7 @@ ;; Renamed all regex to regexp. ;; Got rid of found-start and found-point globals. ;; Generalized handling of upper-case chars. - + ;; Revision 1.2 92/05/27 11:33:57 liberte ;; Emacs version 19 has a search ring, which is supported here. ;; Other fixes found in the version 19 isearch are included here. @@ -100,38 +96,20 @@ ;;; Code: + +;;;========================================================================= +;;; User-accessible variables + (defgroup isearch nil - "Incremental search" + "Incremental search minor mode." :prefix "search-" :group 'matching) -(defun isearch-char-to-string (c) - (if (eventp c) - (make-string 1 (event-to-character c nil nil t)) - (make-string 1 c))) - -;(defun isearch-text-char-description (c) -; (isearch-char-to-string c)) - -(define-function 'isearch-text-char-description 'text-char-description) - - -;;;========================================================================= -;;; User-accessible variables - -(defvar search-last-string "" - "Last string search for by a search command. -This does not include direct calls to the primitive search functions, -and does not include searches that are aborted.") - -(defvar search-last-regexp "" - "Last string searched for by a regexp search command. -This does not include direct calls to the primitive search functions, -and does not include searches that are aborted.") - -(defconst search-exit-option t - "Non-nil means random control characters terminate incremental search.") +(defcustom search-exit-option t + "*Non-nil means random control characters terminate incremental search." + :type 'boolean + :group 'isearch) (defcustom search-slow-window-lines 1 "*Number of lines in slow search display windows. @@ -148,16 +126,70 @@ :type 'integer :group 'isearch) +;; We have `search-caps-disable-folding'. +;(defcustom search-upper-case 'not-yanks +; "*If non-nil, upper case chars disable case fold searching. +;That is, upper and lower case chars must match exactly. +;This applies no matter where the chars come from, but does not +;apply to chars in regexps that are prefixed with `\\'. +;If this value is `not-yanks', yanked text is always downcased." +; :type '(choice (const :tag "off" nil) +; (const not-yanks) +; (other :tag "on" t)) +; :group 'isearch) + (defcustom search-nonincremental-instead t - "*If non-nil, do a nonincremental search instead if exiting immediately." + "*If non-nil, do a nonincremental search instead if exiting immediately. +Actually, `isearch-edit-string' is called to let you enter the search +string, and RET terminates editing and does a nonincremental search." :type 'boolean :group 'isearch) - -(defcustom search-whitespace-regexp "\\(\\s \\|[\n\r]\\)+" + +;; FSF default is "\\s-+", but I think our default is better so I'm +;; leaving it. +(defcustom search-whitespace-regexp "\\(\\s-\\|[\n\r]\\)+" "*If non-nil, regular expression to match a sequence of whitespace chars." :type 'regexp :group 'isearch) +(defcustom search-highlight t + "*Whether incremental search and query-replace should highlight +the text that currently matches the search string." + :type 'boolean + :group 'isearch) + +;; I think the name `search-highlight' makes more sense, both because +;; of consistency with other search-* variables above, and because it +;; also applies to query-replace. +(define-obsolete-variable-alias 'isearch-highlight 'search-highlight) + +(defcustom search-invisible 'open + "If t incremental search can match hidden text. +nil means don't match invisible text. +If the value is `open', if the text matched is made invisible by +an overlay having an `invisible' property and that overlay has a property +`isearch-open-invisible', then incremental search will show the contents. +\(This applies when using `outline.el' and `hideshow.el'.)" + :type '(choice (const :tag "Match hidden text" t) + (const :tag "Open overlays" open) + (const :tag "Don't match hidden text" nil)) + :group 'isearch) + +(defcustom isearch-hide-immediately t + "If non-nil, re-hide an invisible match right away. +This variable makes a difference when `search-invisible' is set to `open'. +It means that after search makes some invisible text visible +to show the match, it makes the text invisible again when the match moves. +Ordinarily the text becomes invisible again at the end of the search." + :type 'boolean + :group 'isearch) + +(defvar isearch-mode-hook nil + "Function(s) to call after starting up an incremental search.") + +(defvar isearch-mode-end-hook nil + "Function(s) to call after terminating an incremental search.") + ;;;================================================================== ;;; Search ring. @@ -175,22 +207,34 @@ :type 'integer :group 'isearch) +;; The important difference between pre-20.4-merge yank-pointers and +;; current code is that the yank pointers positions used to be +;; preserved across the isearch sessions. I changed this because I +;; think the FSF code is closer to how the feature is supposed to +;; behave (read: to minibuffer histories.) (defvar search-ring-yank-pointer nil - "The tail of the search ring whose car is the last thing searched for.") + "Index in `search-ring' of last string reused. +nil if none yet.") (defvar regexp-search-ring-yank-pointer nil - "The tail of the regular expression search ring whose car is the last -thing searched for.") + "Index in `regexp-search-ring' of last string reused. +nil if none yet.") + +(defcustom search-ring-update nil + "*Non-nil if advancing or retreating in the search ring should cause search. +Default nil means edit the string from the search ring first." + :type 'boolean + :group 'isearch) ;;;==================================================== ;;; Define isearch-mode keymap. -(defvar isearch-mode-map +(defvar isearch-mode-map (let ((map (make-keymap))) (set-keymap-name map 'isearch-mode-map) ;; Bind all printing characters to `isearch-printing-char'. - ;; This isn't normally necessary, but if a printing character were - ;; bound to something other than self-insert-command in global-map, + ;; This isn't normally necessary, but if a printing character were + ;; bound to something other than self-insert-command in global-map, ;; then it would terminate the search and be executed without this. (let ((i 32) (str (make-string 1 0))) @@ -198,7 +242,10 @@ (aset str 0 i) (define-key map str 'isearch-printing-char) (setq i (1+ i)))) - (define-key map "\t" 'isearch-printing-char) + + ;; Here FSF sets up various kludges to handle local bindings with + ;; meta char prefix keys. We don't need isearch-other-meta-char + ;; because we handle things differently (via pre-command-hook). ;; Several non-printing chars change the searching behavior. ;; @@ -207,26 +254,29 @@ (define-key map "\C-r" 'isearch-repeat-backward) (define-key map "\C-g" 'isearch-abort) + ;; I wish this worked... + ;(define-key map [escape escape escape] 'isearch-cancel) + (define-key map [(meta escape) escape] 'isearch-cancel) + (define-key map "\C-q" 'isearch-quote-char) (define-key map "\C-m" 'isearch-exit) (define-key map "\C-j" 'isearch-printing-char) (define-key map "\t" 'isearch-printing-char) + ;; I prefer our default. + ;(define-key map " " 'isearch-whitespace-chars) + (define-key map "\M- " 'isearch-whitespace-chars) (define-key map "\C-w" 'isearch-yank-word) (define-key map "\C-y" 'isearch-yank-line) (define-key map "\M-y" 'isearch-yank-kill) - ;; Define keys for regexp chars * ? | + ;; Define keys for regexp chars * ? |. + ;; Nothing special for + because it matches at least once. (define-key map "*" 'isearch-*-char) (define-key map "?" 'isearch-*-char) (define-key map "|" 'isearch-|-char) - ;; Some bindings you may want to put in your isearch-mode-hook. - ;; Suggest some alternates... - ;; (define-key map "\C-t" 'isearch-toggle-regexp) - ;; (define-key map "\C-^" 'isearch-edit-string) - ;; delete and backspace delete backward, f1 is help, and C-h can be either (define-key map 'delete 'isearch-delete-char) (define-key map 'backspace 'isearch-delete-char) @@ -236,15 +286,23 @@ (define-key map "\M-n" 'isearch-ring-advance) (define-key map "\M-p" 'isearch-ring-retreat) - (define-key map "\M- " 'isearch-whitespace-chars) (define-key map "\M-\t" 'isearch-complete) - (define-key map 'button2 'isearch-yank-x-selection) + ;; I find this binding somewhat unintuitive, because it doesn't + ;; work if the mouse pointer is over the echo area -- it has to be + ;; over the search window. + (define-key map 'button2 'isearch-yank-selection) map) "Keymap for isearch-mode.") -(defvar minibuffer-local-isearch-map +;; Some bindings you may want to put in your isearch-mode-hook. +;; Suggest some alternates... +;; (define-key isearch-mode-map "\C-t" 'isearch-toggle-case-fold) +;; (define-key isearch-mode-map "\C-t" 'isearch-toggle-regexp) +;; (define-key isearch-mode-map "\C-^" 'isearch-edit-string) + +(defvar minibuffer-local-isearch-map (let ((map (make-sparse-keymap))) ;; #### - this should also be minor-mode-ified (set-keymap-parents map (list minibuffer-local-map)) @@ -254,6 +312,8 @@ (define-key map "\r" 'isearch-nonincremental-exit-minibuffer) (define-key map "\M-n" 'isearch-ring-advance-edit) (define-key map "\M-p" 'isearch-ring-retreat-edit) + (define-key map 'down 'isearch-ring-advance-edit) + (define-key map 'up 'isearch-ring-retreat-edit) (define-key map "\M-\t" 'isearch-complete-edit) (define-key map "\C-s" 'isearch-forward-exit-minibuffer) (define-key map "\C-r" 'isearch-reverse-exit-minibuffer) @@ -262,7 +322,8 @@ ;;;======================================================== ;; Internal variables declared globally for byte-compiler. -;; These are all bound locally while editing the search string. +;; These are all set with setq while isearching +;; and bound locally while editing the search string. (defvar isearch-forward nil) ; Searching in the forward direction. (defvar isearch-regexp nil) ; Searching for a regexp. @@ -274,6 +335,7 @@ (defvar isearch-success t) ; Searching is currently successful. (defvar isearch-invalid-regexp nil) ; Regexp not well formed. +(defvar isearch-within-brackets nil) ; Regexp has unclosed [. (defvar isearch-other-end nil) ; Start (end) of match if forward (backward). (defvar isearch-wrapped nil) ; Searching restarted from the top (bottom). (defvar isearch-barrier 0) @@ -282,6 +344,12 @@ (defvar isearch-case-fold-search nil) +;; Need this for toggling case in isearch-toggle-case-fold. When this +;; is non-nil, the case-sensitiveness of the search is set by the +;; user, and is may no longer be dynamically changed as per +;; search-caps-disable-folding. +(defvar isearch-fixed-case nil) + (defvar isearch-adjusted nil) (defvar isearch-slow-terminal-mode nil) ;;; If t, using a small window. @@ -308,12 +376,9 @@ ;; New value of isearch-forward after isearch-edit-string. (defvar isearch-new-forward nil) +;; Accumulate here the extents unhidden during searching. +(defvar isearch-unhidden-extents nil) ; in FSF: isearch-opened-overlays -(defvar isearch-mode-hook nil - "Function(s) to call after starting up an incremental search.") - -(defvar isearch-mode-end-hook nil - "Function(s) to call after terminating an incremental search.") ;;;============================================================== ;; Minor-mode-alist changes - kind of redundant with the @@ -321,21 +386,28 @@ (add-minor-mode 'isearch-mode 'isearch-mode) -(defvar isearch-mode nil) +(defvar isearch-mode nil) ;; Name of the minor mode, if non-nil. (make-variable-buffer-local 'isearch-mode) +;; We bind these in keydefs.el. +;(define-key global-map "\C-s" 'isearch-forward) +;(define-key global-map "\C-r" 'isearch-backward) +;(define-key global-map "\M-\C-s" 'isearch-forward-regexp) +;(define-key global-map "\M-\C-r" 'isearch-backward-regexp) + ;;;=============================================================== ;;; Entry points to isearch-mode. ;;; These four functions should replace those in loaddefs.el -;;; An alternative is to fset isearch-forward etc to isearch-mode, -;;; and look at the last command to set the options accordingly. +;;; An alternative is to defalias isearch-forward etc to isearch-mode, +;;; and look at this-command to set the options accordingly. -(defun isearch-forward (&optional regexp-p) - "Do incremental search forward. +(defun isearch-forward (&optional regexp-p no-recursive-edit) + "\ +Do incremental search forward. With a prefix argument, do an incremental regular expression search instead. \\ As you type characters, they add to the search string and are found. -The following non-printing keys are bound in `isearch-mode-map'. +The following non-printing keys are bound in `isearch-mode-map'. Type \\[isearch-delete-char] to cancel characters from end of search string. Type \\[isearch-exit] to exit, leaving point at location found. @@ -346,6 +418,8 @@ string and search for it. Type \\[isearch-yank-line] to yank rest of line onto end of search string\ and search for it. +Type \\[isearch-yank-kill] to yank last killed text onto end of search string\ + and search for it. Type \\[isearch-quote-char] to quote control character to search for it. Type \\[isearch-whitespace-chars] to match all whitespace chars in regexp. \\[isearch-abort] while searching or when search has failed cancels input\ @@ -377,36 +451,38 @@ ;; Type \\[isearch-edit-string] to edit the search string in the minibuffer. ;; Terminate editing and return to incremental searching with CR. - (interactive "_P") - (isearch-mode t (not (null regexp-p)) nil (not (interactive-p)))) + (interactive "_P\np") + (isearch-mode t (not (null regexp-p)) nil (not no-recursive-edit))) -(defun isearch-forward-regexp () +(defun isearch-forward-regexp (&optional not-regexp no-recursive-edit) "\ Do incremental search forward for regular expression. +With a prefix argument, do a regular string search instead. Like ordinary incremental search except that your input is treated as a regexp. See \\[isearch-forward] for more info." - (interactive "_") - (isearch-mode t t nil (not (interactive-p)))) + (interactive "_P\np") + (isearch-mode t (null not-regexp) nil (not no-recursive-edit))) -(defun isearch-backward (&optional regexp-p) +(defun isearch-backward (&optional regexp-p no-recursive-edit) "\ Do incremental search backward. -With a prefix argument, do an incremental regular expression search instead. +With a prefix argument, do a regular expression search instead. See \\[isearch-forward] for more information." - (interactive "_P") - (isearch-mode nil (not (null regexp-p)) nil (not (interactive-p)))) + (interactive "_P\np") + (isearch-mode nil (not (null regexp-p)) nil (not no-recursive-edit))) -(defun isearch-backward-regexp () +(defun isearch-backward-regexp (&optional not-regexp no-recursive-edit) "\ Do incremental search backward for regular expression. +With a prefix argument, do a regular string search instead. Like ordinary incremental search except that your input is treated as a regexp. See \\[isearch-forward] for more info." - (interactive "_") - (isearch-mode nil t nil (not (interactive-p)))) + (interactive "_P\np") + (isearch-mode nil (null not-regexp) nil (not no-recursive-edit))) -;; This function is way wrong, because you can't scroll the help -;; screen; as soon as you press a key, it's gone. I don't know of a -;; good way to fix it, though. -hniksic +;; The problem here is that you can't scroll the help screen; as soon +;; as you press a key, it's gone. I don't know of a good way to fix +;; it, though. -hniksic (defun isearch-mode-help () (interactive "_") (let ((w (selected-window))) @@ -420,7 +496,9 @@ ;; All the work is done by the isearch-mode commands. (defun isearch-mode (forward &optional regexp op-fun recursive-edit word-p) - "Start isearch minor mode. Called by isearch-forward, etc." + "Start isearch minor mode. Called by `isearch-forward', etc. + +\\{isearch-mode-map}" (if executing-kbd-macro (setq recursive-edit nil)) @@ -433,6 +511,7 @@ isearch-word word-p isearch-op-fun op-fun isearch-case-fold-search case-fold-search + isearch-fixed-case nil isearch-string "" isearch-message "" isearch-cmds nil @@ -442,6 +521,7 @@ isearch-adjusted nil isearch-yank-flag nil isearch-invalid-regexp nil + isearch-within-brackets nil isearch-slow-terminal-mode (and (<= (device-baud-rate) search-slow-speed) (> (window-height) @@ -451,10 +531,14 @@ isearch-just-started t isearch-opoint (point) + search-ring-yank-pointer nil + regexp-search-ring-yank-pointer nil + isearch-opened-extents nil isearch-window-configuration (current-window-configuration) - ;; #### Should we remember the old value of - ;; overriding-local-map? + ;; #### What we really need is a buffer-local + ;; overriding-local-map. See isearch-pre-command-hook for + ;; more details. overriding-local-map (progn (set-keymap-parents isearch-mode-map (nconc (current-minor-mode-maps) @@ -463,7 +547,6 @@ isearch-mode-map) isearch-selected-frame (selected-frame) - isearch-mode (gettext " Isearch") ) ;; XEmacs change: without clearing the match data, sometimes old values @@ -471,7 +554,10 @@ (store-match-data nil) (add-hook 'pre-command-hook 'isearch-pre-command-hook) - (set-buffer-modified-p (buffer-modified-p)) ; update modeline + + (setq isearch-mode (gettext " Isearch")) + (redraw-modeline) + (isearch-push-state) ) ; inhibit-quit is t before here @@ -479,26 +565,26 @@ (isearch-update) (run-hooks 'isearch-mode-hook) - ;; isearch-mode can be made modal (in the sense of not returning to - ;; the calling function until searching is completed) by entering + ;; isearch-mode can be made modal (in the sense of not returning to + ;; the calling function until searching is completed) by entering ;; a recursive-edit and exiting it when done isearching. (if recursive-edit (let ((isearch-recursive-edit t)) (recursive-edit))) - ) + isearch-success) ;;;==================================================== ;; Some high level utilities. Others below. (defun isearch-update () - ;; Called after each command to update the display. - (if (null unread-command-event) + ;; Called after each command to update the display. + (if (null unread-command-events) (progn (if (not (input-pending-p)) (isearch-message)) (if (and isearch-slow-terminal-mode - (not (or isearch-small-window + (not (or isearch-small-window (pos-visible-in-window-p)))) (let ((found-point (point))) (setq isearch-small-window t) @@ -520,27 +606,24 @@ (if (< isearch-other-end (point)) (isearch-highlight isearch-other-end (point)) (isearch-highlight (point) isearch-other-end)) - (if (extentp isearch-extent) - (isearch-dehighlight nil))) + (isearch-dehighlight)) )) (setq ;; quit-flag nil not for isearch-mode isearch-adjusted nil isearch-yank-flag nil) + (isearch-highlight-all-update) ) -(defun isearch-done () +(defun isearch-done (&optional nopush edit) ;; Called by all commands that terminate isearch-mode. (let ((inhibit-quit t)) ; danger danger! (if (and isearch-buffer (buffer-live-p isearch-buffer)) - (save-excursion - ;; Some loser process filter might have switched the - ;; window's buffer, so be sure to set these variables back - ;; in the buffer we frobbed them in. But only if the buffer - ;; is still alive. - (set-buffer isearch-buffer) - ;; #### Should we restore the old value of - ;; overriding-local-map? + ;; Some loser process filter might have switched the window's + ;; buffer, so be sure to set these variables back in the + ;; buffer we frobbed them in. But only if the buffer is still + ;; alive. + (with-current-buffer isearch-buffer (setq overriding-local-map nil) ;; Use remove-hook instead of just setting it to our saved value ;; in case some process filter has created a buffer and modified @@ -549,8 +632,11 @@ (remove-hook 'pre-command-hook 'isearch-pre-command-hook) (set-keymap-parents isearch-mode-map nil) (setq isearch-mode nil) - (set-buffer-modified-p (buffer-modified-p));; update modeline - (isearch-dehighlight t))) + (redraw-modeline) + (isearch-dehighlight) + (isearch-highlight-all-cleanup) + (isearch-restore-invisible-extents nil nil) + )) ;; it's not critical that this be inside inhibit-quit, but leaving ;; things in small-window-mode would be bad. @@ -568,37 +654,41 @@ ;; Maybe should test difference between and set mark iff > threshold. (if (and (buffer-live-p isearch-buffer) (/= (point isearch-buffer) isearch-opoint)) + ;; #### FSF doesn't do this if the region is active. Should + ;; we do the same? (progn (push-mark isearch-opoint t nil isearch-buffer) (or executing-kbd-macro (> (minibuffer-depth) 0) - (display-message 'command "Mark saved where search started")))) - ) + (display-message 'command "Mark saved where search started"))))) (setq isearch-buffer nil) ) ; inhibit-quit is t before here - (if (> (length isearch-string) 0) + (if (and (> (length isearch-string) 0) (not nopush)) ;; Update the ring data. - (if isearch-regexp - (if (not (setq regexp-search-ring-yank-pointer - (member isearch-string regexp-search-ring))) - (progn - (setq regexp-search-ring - (cons isearch-string regexp-search-ring) - regexp-search-ring-yank-pointer regexp-search-ring) - (if (> (length regexp-search-ring) regexp-search-ring-max) - (setcdr (nthcdr (1- regexp-search-ring-max) regexp-search-ring) - nil)))) - (if (not (setq search-ring-yank-pointer - ;; really need equal test instead of eq. - (member isearch-string search-ring))) - (progn - (setq search-ring (cons isearch-string search-ring) - search-ring-yank-pointer search-ring) - (if (> (length search-ring) search-ring-max) - (setcdr (nthcdr (1- search-ring-max) search-ring) nil)))))) + (isearch-update-ring isearch-string isearch-regexp)) (run-hooks 'isearch-mode-end-hook) - (if isearch-recursive-edit (exit-recursive-edit))) + + (and (not edit) isearch-recursive-edit (exit-recursive-edit))) + +(defun isearch-update-ring (string &optional regexp) + "Add STRING to the beginning of the search ring. +REGEXP says which ring to use." + (if regexp + (if (or (null regexp-search-ring) + (not (string= string (car regexp-search-ring)))) + (progn + (setq regexp-search-ring + (cons string regexp-search-ring)) + (if (> (length regexp-search-ring) regexp-search-ring-max) + (setcdr (nthcdr (1- search-ring-max) regexp-search-ring) + nil)))) + (if (or (null search-ring) + (not (string= string (car search-ring)))) + (progn + (setq search-ring (cons string search-ring)) + (if (> (length search-ring) search-ring-max) + (setcdr (nthcdr (1- search-ring-max) search-ring) nil)))))) ;;;==================================================== @@ -607,12 +697,16 @@ (defun isearch-exit () "Exit search normally. However, if this is the first command after starting incremental -search and `search-nonincremental-instead' is non-nil, do an -incremental search via `isearch-edit-string'." +search and `search-nonincremental-instead' is non-nil, do a +nonincremental search instead via `isearch-edit-string'." (interactive) - (if (and search-nonincremental-instead + (if (and search-nonincremental-instead (= 0 (length isearch-string))) - (let ((isearch-nonincremental t)) + (let ((isearch-nonincremental t) + ;; Highlighting only gets in the way of nonincremental + ;; search. + (search-highlight nil) + (isearch-highlight-all-matches nil)) (isearch-edit-string)) (isearch-done))) @@ -621,115 +715,112 @@ "Edit the search string in the minibuffer. The following additional command keys are active while editing. \\ -\\[exit-minibuffer] to exit editing and resume incremental searching. +\\[exit-minibuffer] to resume incremental searching with the edited string. +\\[isearch-nonincremental-exit-minibuffer] to do one nonincremental search. \\[isearch-forward-exit-minibuffer] to resume isearching forward. -\\[isearch-backward-exit-minibuffer] to resume isearching backward. -\\[isearch-ring-advance-edit] to replace the search string with the next\ - item in the search ring. -\\[isearch-ring-retreat-edit] to replace the search string with the next\ - item in the search ring. -\\[isearch-complete-edit] to complete the search string from the search ring." +\\[isearch-reverse-exit-minibuffer] to resume isearching backward. +\\[isearch-ring-advance-edit] to replace the search string with the next item in the search ring. +\\[isearch-ring-retreat-edit] to replace the search string with the previous item in the search ring. +\\[isearch-complete-edit] to complete the search string using the search ring. +\\ +If first char entered is \\[isearch-yank-word], then do word search instead." + ;; This code is very hairy for several reasons, explained in the code. + ;; Mainly, isearch-mode must be terminated while editing and then restarted. + ;; If there were a way to catch any change of buffer from the minibuffer, + ;; this could be simplified greatly. ;; Editing doesn't back up the search point. Should it? (interactive) (condition-case nil - (let ((minibuffer-local-map minibuffer-local-isearch-map) - isearch-nonincremental ; should search nonincrementally? - isearch-new-string - isearch-new-message - (isearch-new-forward isearch-forward) + (progn + (let ((isearch-nonincremental isearch-nonincremental) - ;; Locally bind all isearch global variables to protect them - ;; from recursive isearching. - (isearch-string isearch-string) - (isearch-message isearch-message) - (isearch-forward isearch-forward) ; set by commands below. + ;; Locally bind all isearch global variables to protect them + ;; from recursive isearching. + ;; isearch-string -message and -forward are not bound + ;; so they may be changed. Instead, save the values. + (isearch-new-string isearch-string) + (isearch-new-message isearch-message) + (isearch-new-forward isearch-forward) + (isearch-new-word isearch-word) - (isearch-forward isearch-forward) - (isearch-regexp isearch-regexp) - (isearch-word isearch-word) - (isearch-op-fun isearch-op-fun) - (isearch-cmds isearch-cmds) - (isearch-success isearch-success) - (isearch-wrapped isearch-wrapped) - (isearch-barrier isearch-barrier) - (isearch-adjusted isearch-adjusted) - (isearch-yank-flag isearch-yank-flag) - (isearch-invalid-regexp isearch-invalid-regexp) - (isearch-other-end isearch-other-end) - (isearch-opoint isearch-opoint) - (isearch-slow-terminal-mode isearch-slow-terminal-mode) - (isearch-small-window isearch-small-window) - (isearch-recursive-edit isearch-recursive-edit) - (isearch-window-configuration (current-window-configuration)) - (isearch-selected-frame (selected-frame)) - ) - ;; Actually terminate isearching until editing is done. - ;; This is so that the user can do anything without failure, - ;; like switch buffers and start another isearch, and return. + (isearch-regexp isearch-regexp) + (isearch-op-fun isearch-op-fun) + (isearch-cmds isearch-cmds) + (isearch-success isearch-success) + (isearch-wrapped isearch-wrapped) + (isearch-barrier isearch-barrier) + (isearch-adjusted isearch-adjusted) + (isearch-fixed-case isearch-fixed-case) + (isearch-yank-flag isearch-yank-flag) + (isearch-invalid-regexp isearch-invalid-regexp) + (isearch-within-brackets isearch-within-brackets) + ;;; Don't bind this. We want isearch-search, below, to set it. + ;;; And the old value won't matter after that. + ;;; (isearch-other-end isearch-other-end) + (isearch-opoint isearch-opoint) + (isearch-slow-terminal-mode isearch-slow-terminal-mode) + (isearch-small-window isearch-small-window) + (isearch-recursive-edit isearch-recursive-edit) + (isearch-window-configuration (current-window-configuration)) + (isearch-selected-frame (selected-frame)) + ) + ;; Actually terminate isearching until editing is done. + ;; This is so that the user can do anything without failure, + ;; like switch buffers and start another isearch, and return. ;; (condition-case nil - (isearch-done) + (isearch-done t t) ;;#### What does this mean? There is no such condition! -;; (exit nil)) ; was recursive editing +;; (exit nil)) ; was recursive editing - (unwind-protect - (let ((prompt (isearch-message-prefix nil t)) - event) - ;; If the first character the user types when we prompt them - ;; for a string is the yank-word character, then go into - ;; word-search mode. Otherwise unread that character and - ;; read a string the normal way. - (let ((cursor-in-echo-area t)) - (display-message 'prompt prompt) - (setq event (next-command-event)) - (if (eq 'isearch-yank-word - (lookup-key isearch-mode-map (vector event))) - (setq isearch-word t) - (setq unread-command-event event))) - (setq isearch-new-string -;; (if (fboundp 'gmhist-old-read-from-minibuffer) -;; ;; Eschew gmhist crockery -;; (gmhist-old-read-from-minibuffer prompt isearch-string) - (read-string - prompt isearch-string - 't ;does its own history (but shouldn't) -;; (if isearch-regexp -;; ;; The search-rings aren't exactly minibuffer -;; ;; histories, but they are close enough -;; (cons 'regexp-search-ring -;; (- (length regexp-search-ring-yank-pointer) -;; (length regexp-search-ring))) -;; (cons 'search-ring -;; (- (length search-ring-yank-pointer) -;; (length search-ring)))) + (unwind-protect + (progn + ;; Fake the prompt message for the sake of + ;; next-command-event below. + (isearch-message) + ;; If the first character the user types when we + ;; prompt them for a string is the yank-word + ;; character, then go into word-search mode. + ;; Otherwise unread that character and read a string + ;; the normal way. + (let* ((cursor-in-echo-area t) + (event (next-command-event))) + (if (eq 'isearch-yank-word + (lookup-key isearch-mode-map (vector event))) + (setq isearch-word t;; so message-prefix is right + isearch-new-word t) + (setq unread-command-event event))) + (setq isearch-new-string + (read-from-minibuffer + (isearch-message-prefix nil isearch-nonincremental) + isearch-string + minibuffer-local-isearch-map + nil + 't ;does its own history (but shouldn't) ) -;; ) - isearch-new-message (mapconcat - 'isearch-text-char-description - isearch-new-string "")) - ) - ;; Always resume isearching by restarting it. - (isearch-mode isearch-forward - isearch-regexp - isearch-op-fun - isearch-recursive-edit - isearch-word) - ) + isearch-new-message (mapconcat + 'isearch-text-char-description + isearch-new-string ""))) + ;; Always resume isearching by restarting it. + (isearch-mode isearch-forward + isearch-regexp + isearch-op-fun + isearch-recursive-edit + isearch-word) - ;; Copy new values in outer locals to isearch globals - (setq isearch-string isearch-new-string - isearch-message isearch-new-message - isearch-forward isearch-new-forward) + ;; Copy new values in outer locals to isearch globals + (setq isearch-string isearch-new-string + isearch-message isearch-new-message + isearch-forward isearch-new-forward + isearch-word isearch-new-word)) - ;; Empty isearch-string means use default. - (if (= 0 (length isearch-string)) - (setq isearch-string (if isearch-regexp search-last-regexp - search-last-string)) - ;; Set last search string now so it is set even if we fail. - (if search-last-regexp - (setq search-last-regexp isearch-string) - (setq search-last-string isearch-string))) + ;; Empty isearch-string means use default. + (if (= 0 (length isearch-string)) + (setq isearch-string (or (car (if isearch-regexp + regexp-search-ring + search-ring)) + "")))) ;; Reinvoke the pending search. (isearch-push-state) @@ -756,25 +847,33 @@ (setq isearch-new-forward nil) (exit-minibuffer)) +(defun isearch-cancel () + "Terminate the search and go back to the starting point." + (interactive) + (goto-char isearch-opoint) + (isearch-done t) + (signal 'quit '(isearch))) ; and pass on quit signal (defun isearch-abort () - "Quit incremental search mode if searching is successful, signalling quit. + "Abort incremental search mode if searching is successful, signaling quit. Otherwise, revert to previous successful search and continue searching. -Use `isearch-exit' to quit without signalling." +Use `isearch-exit' to quit without signaling." (interactive) -;; (ding) signal instead below, if quiting +;; (ding) signal instead below, if quitting (discard-input) (if isearch-success ;; If search is successful, move back to starting point ;; and really do quit. (progn (goto-char isearch-opoint) - (isearch-done) ; exit isearch + (setq isearch-success nil) + (isearch-done t) ; exit isearch (signal 'quit '(isearch))) ; and pass on quit signal - ;; If search is failing, rub out until it is once more successful. - (while (not isearch-success) (isearch-pop-state)) + ;; If search is failing, or has an incomplete regexp, + ;; rub out until it is once more successful. + (while (or (not isearch-success) isearch-invalid-regexp) + (isearch-pop-state)) (isearch-update))) - (defun isearch-repeat (direction) ;; Utility for isearch-repeat-forward and -backward. (if (eq isearch-forward (eq direction 'forward)) @@ -783,35 +882,30 @@ ;; If search string is empty, use last one. (setq isearch-string (or (if isearch-regexp - (if regexp-search-ring-yank-pointer - (car regexp-search-ring-yank-pointer) - (car regexp-search-ring)) - (if search-ring-yank-pointer - (car search-ring-yank-pointer) - (car search-ring))) + (car regexp-search-ring) + (car search-ring)) "") isearch-message (mapconcat 'isearch-text-char-description isearch-string "")) ;; If already have what to search for, repeat it. (or isearch-success - (progn - + (progn (goto-char (if isearch-forward (point-min) (point-max))) (setq isearch-wrapped t)))) ;; C-s in reverse or C-r in forward, change direction. (setq isearch-forward (not isearch-forward))) (setq isearch-barrier (point)) ; For subsequent \| if regexp. + (if (equal isearch-string "") (setq isearch-success t) - (if (and (equal (match-end 0) (match-beginning 0)) - isearch-success + (if (and isearch-success (equal (match-end 0) (match-beginning 0)) (not isearch-just-started)) ;; If repeating a search that found ;; an empty string, ensure we advance. (if (if isearch-forward (eobp) (bobp)) - ;; nowhere to advance to, so fail (and wrap next time) + ;; If there's nowhere to advance to, fail (and wrap next time). (progn (setq isearch-success nil) (and executing-kbd-macro @@ -821,6 +915,7 @@ (forward-char (if isearch-forward 1 -1)) (isearch-search)) (isearch-search))) + (isearch-push-state) (isearch-update)) @@ -845,18 +940,21 @@ (defun isearch-toggle-case-fold () "Toggle case folding in searching on or off." (interactive) - (setq isearch-case-fold-search - (if isearch-case-fold-search nil 'yes)) - (message "%s%s [case %ssensitive]" - (isearch-message-prefix) - isearch-message - (if isearch-case-fold-search "in" "")) + (setq isearch-case-fold-search (if isearch-case-fold-search nil 'yes) + isearch-fixed-case t) + (lmessage 'progress "%s%s [case %ssensitive]" + (isearch-message-prefix) + isearch-message + (if isearch-case-fold-search "in" "")) (setq isearch-adjusted t) + ;; Update the highlighting here so that it gets done before the + ;; one-second pause. + (isearch-highlight-all-update) (sit-for 1) (isearch-update)) (defun isearch-delete-char () - "Discard last input item and move point back. + "Discard last input item and move point back. If no previous match was done, just beep." (interactive) (if (null (cdr isearch-cmds)) @@ -876,6 +974,7 @@ (isearch-delete-char) (isearch-mode-help))) +;; This is similar to FSF isearch-yank-string, but more general. (defun isearch-yank (chunk) ;; Helper for isearch-yank-* functions. CHUNK can be a string or a ;; function. @@ -886,7 +985,7 @@ (goto-char isearch-other-end)) (buffer-substring (point) - (save-excursion + (progn (funcall chunk) (point))))))) ;; if configured so that typing upper-case characters turns off case @@ -904,7 +1003,6 @@ isearch-yank-flag t)) (isearch-search-and-update)) - (defun isearch-yank-word () "Pull next word from buffer into search string." (interactive) @@ -925,30 +1023,34 @@ (interactive) (isearch-yank 'forward-sexp)) -(defun isearch-yank-x-selection () - "Pull the current X selection into the search string." +(defun isearch-yank-selection () + "Pull the current selection into the search string." (interactive) - (isearch-yank (x-get-selection))) + (isearch-yank (get-selection))) -(defun isearch-yank-x-clipboard () - "Pull the current X clipboard selection into the search string." +(defun isearch-yank-clipboard () + "Pull the current clipboard selection into the search string." (interactive) - (isearch-yank (x-get-clipboard))) + (isearch-yank (get-clipboard))) (defun isearch-fix-case () - (if (and isearch-case-fold-search search-caps-disable-folding) - (setq isearch-case-fold-search + ;; The commented-out (and ...) form implies that, once + ;; isearch-case-fold-search becomes nil due to a capital letter + ;; typed in, it can never be restored to the original value. In + ;; that case, it's impossible to revert a case-sensitive search back + ;; to case-insensitive. + (if ;(and isearch-case-fold-search search-caps-disable-folding) + (and case-fold-search + ;; Make sure isearch-toggle-case-fold works. + (not isearch-fixed-case) + search-caps-disable-folding) + (setq isearch-case-fold-search (no-upper-case-p isearch-string isearch-regexp))) (setq isearch-mode (if case-fold-search (if isearch-case-fold-search " Isearch" ;As God Intended Mode " ISeARch") ;Warn about evil case via StuDLYcAps. - "Isearch" -; (if isearch-case-fold-search -; " isearch" ;Presumably case-sensitive losers -; ;will notice this 1-char difference. -; " Isearch") ;Weenie mode. - ))) + " Isearch"))) (defun isearch-search-and-update () ;; Do the search and update the display. @@ -972,16 +1074,17 @@ (regexp-quote isearch-string))))) (error nil)) (or isearch-yank-flag - (<= (match-end 0) + (<= (match-end 0) (min isearch-opoint isearch-barrier)))) - (setq isearch-success t + (setq isearch-success t isearch-invalid-regexp nil + isearch-within-brackets nil isearch-other-end (match-end 0)) ;; Not regexp, not reverse, or no match at point. (if (and isearch-other-end (not isearch-adjusted)) (goto-char (if isearch-forward isearch-other-end - (min isearch-opoint - isearch-barrier + (min isearch-opoint + isearch-barrier (1+ isearch-other-end))))) (isearch-search) )) @@ -991,31 +1094,34 @@ ;; *, ?, and | chars can make a regexp more liberal. -;; They can make a regexp match sooner -;; or make it succeed instead of failing. +;; They can make a regexp match sooner or make it succeed instead of failing. ;; So go back to place last successful search started ;; or to the last ^S/^R (barrier), whichever is nearer. +;; + needs no special handling because the string must match at least once. (defun isearch-*-char () "Handle * and ? specially in regexps." (interactive) - (if isearch-regexp - - (progn - (setq isearch-adjusted t) - (let ((cs (nth (if isearch-forward - 5 ; isearch-other-end - 2) ; saved (point) - (car (cdr isearch-cmds))))) + (if isearch-regexp + (let ((idx (length isearch-string))) + (while (and (> idx 0) + (eq (aref isearch-string (1- idx)) ?\\)) + (setq idx (1- idx))) + (when (= (mod (- (length isearch-string) idx) 2) 0) + (setq isearch-adjusted t) + ;; Get the isearch-other-end from before the last search. + ;; We want to start from there, + ;; so that we don't retreat farther than that. ;; (car isearch-cmds) is after last search; ;; (car (cdr isearch-cmds)) is from before it. - (setq cs (or cs isearch-barrier)) - (goto-char - (if isearch-forward - (max cs isearch-barrier) - (min cs isearch-barrier)))))) + (let ((cs (nth 5 (car (cdr isearch-cmds))))) + (setq cs (or cs isearch-barrier)) + (goto-char + (if isearch-forward + (max cs isearch-barrier) + (min cs isearch-barrier))))))) (isearch-process-search-char last-command-event)) - + (defun isearch-|-char () @@ -1027,42 +1133,59 @@ (goto-char isearch-barrier))) (isearch-process-search-char last-command-event)) +;; FSF: +;(defalias 'isearch-other-control-char 'isearch-other-meta-char) +; +;(defun isearch-other-meta-char () +;... +; + (defun isearch-quote-char () "Quote special characters for incremental search." (interactive) + ;; #### Here FSF does some special conversion of chars in 0200-0377 + ;; range. Maybe we should do the same. (isearch-process-search-char (read-quoted-char (isearch-message t)))) - (defun isearch-return-char () "Convert return into newline for incremental search. Obsolete." (interactive) (isearch-process-search-char ?\n)) - (defun isearch-printing-char () - "Any other printing character => add it to the search string and search." + "Add this ordinary printing character to the search string and search." (interactive) - (isearch-process-search-char last-command-event)) - + (let ((event last-command-event)) + ;; If we are called by isearch-whitespace-chars because the + ;; context disallows whitespace search (e.g. within brackets), + ;; replace M-SPC with a space. FSF has similar code. + (and (eq this-command 'isearch-whitespace-chars) + (null (event-to-character event)) + (setq event (character-to-event ?\ ))) + (isearch-process-search-char event))) (defun isearch-whitespace-chars () "Match all whitespace chars, if in regexp mode." + ;; FSF docstring adds: "If you want to search for just a space, type + ;; C-q SPC." But we don't need the addition because we have a + ;; different (better) default for the variable. (interactive) - (if (and isearch-regexp search-whitespace-regexp) - (isearch-process-search-string search-whitespace-regexp " ") - (beep) - (isearch-process-search-char ?\ ) -; (if isearch-word -; nil -; (setq isearch-word t) -; (goto-char isearch-other-end) -; (isearch-process-search-char ?\ )) - )) + (if isearch-regexp + (if (and search-whitespace-regexp (not isearch-within-brackets) + (not isearch-invalid-regexp)) + (isearch-process-search-string search-whitespace-regexp " ") + (isearch-printing-char)) + (progn + ;; This way of doing word search doesn't correctly extend current search. + ;; (setq isearch-word t) + ;; (setq isearch-adjusted t) + ;; (goto-char isearch-barrier) + (isearch-printing-char)))) (defun isearch-process-search-char (char) ;; Append the char to the search string, update the message and re-search. - (isearch-process-search-string (isearch-char-to-string char) + (isearch-process-search-string (isearch-char-to-string char) (isearch-text-char-description char))) (defun isearch-process-search-string (string message) @@ -1074,12 +1197,6 @@ ;;=========================================================== ;; Search Ring -(defcustom search-ring-update nil - "*Non-nil if advancing or retreating in the search ring should cause search. -Default nil means edit the string from the search ring first." - :type 'boolean - :group 'isearch) - (defun isearch-ring-adjust1 (advance) ;; Helper for isearch-ring-adjust (let* ((ring (if isearch-regexp regexp-search-ring search-ring)) @@ -1092,25 +1209,25 @@ () (set yank-pointer-name (setq yank-pointer - (nthcdr (% (+ (- length (length yank-pointer)) - (if advance (1- length) 1)) - length) ring))) - (setq isearch-string (car yank-pointer) + (mod (+ (or yank-pointer 0) + (if advance -1 1)) + length))) + (setq isearch-string (nth yank-pointer ring) isearch-message (mapconcat 'isearch-text-char-description isearch-string ""))))) (defun isearch-ring-adjust (advance) ;; Helper for isearch-ring-advance and isearch-ring-retreat - (if (cdr isearch-cmds) ;; is there more than one thing on stack? - (isearch-pop-state)) +; (if (cdr isearch-cmds) ;; is there more than one thing on stack? +; (isearch-pop-state)) (isearch-ring-adjust1 advance) - (isearch-push-state) (if search-ring-update (progn (isearch-search) (isearch-update)) (isearch-edit-string) - )) + ) + (isearch-push-state)) (defun isearch-ring-advance () "Advance to the next search string in the ring." @@ -1123,30 +1240,59 @@ (interactive) (isearch-ring-adjust nil)) -(defun isearch-ring-adjust-edit (advance) - "Use the next or previous search string in the ring while in minibuffer." - (isearch-ring-adjust1 advance) - (erase-buffer) - (insert isearch-string)) +(defun isearch-ring-advance-edit (n) + "Insert the next element of the search history into the minibuffer." + (interactive "p") + (let* ((yank-pointer-name (if isearch-regexp + 'regexp-search-ring-yank-pointer + 'search-ring-yank-pointer)) + (yank-pointer (eval yank-pointer-name)) + (ring (if isearch-regexp regexp-search-ring search-ring)) + (length (length ring))) + (if (zerop length) + () + (set yank-pointer-name + (setq yank-pointer + (mod (- (or yank-pointer 0) n) + length))) + + (erase-buffer) + (insert (nth yank-pointer ring)) + (goto-char (point-max))))) -(defun isearch-ring-advance-edit () - (interactive) - (isearch-ring-adjust-edit 'advance)) +(defun isearch-ring-retreat-edit (n) + "Inserts the previous element of the search history into the minibuffer." + (interactive "p") + (isearch-ring-advance-edit (- n))) + +;; Merging note: FSF comments out these functions and implements them +;; differently (see above), presumably because the versions below mess +;; with isearch-string, while what we really want them to do is simply +;; to insert the correct string to the minibuffer. -(defun isearch-ring-retreat-edit () - "Retreat to the previous search string in the ring while in the minibuffer." - (interactive) - (isearch-ring-adjust-edit nil)) +;;(defun isearch-ring-adjust-edit (advance) +;; "Use the next or previous search string in the ring while in minibuffer." +;; (isearch-ring-adjust1 advance) +;; (erase-buffer) +;; (insert isearch-string)) + +;;(defun isearch-ring-advance-edit () +;; (interactive) +;; (isearch-ring-adjust-edit 'advance)) + +;;(defun isearch-ring-retreat-edit () +;; "Retreat to the previous search string in the ring while in the minibuffer." +;; (interactive) +;; (isearch-ring-adjust-edit nil)) (defun isearch-complete1 () ;; Helper for isearch-complete and isearch-complete-edit - ;; Return t if completion OK, + ;; Return t if completion OK, nil if no completion exists. (let* ((ring (if isearch-regexp regexp-search-ring search-ring)) (alist (mapcar (function (lambda (string) (list string))) ring)) (completion-ignore-case case-fold-search) - (completion (try-completion isearch-string alist)) - ) + (completion (try-completion isearch-string alist))) (cond ((eq completion t) ;; isearch-string stays the same @@ -1154,12 +1300,14 @@ ((or completion ; not nil, must be a string (= 0 (length isearch-string))) ; shouldn't have to say this (if (equal completion isearch-string) ;; no extension? - (if completion-auto-help - (with-output-to-temp-buffer "*Isearch completions*" - (display-completion-list - (all-completions isearch-string alist)))) - (setq isearch-string completion)) - t) + (progn + (if completion-auto-help + (with-output-to-temp-buffer "*Isearch completions*" + (display-completion-list + (all-completions isearch-string alist)))) + t) + (and completion + (setq isearch-string completion)))) (t (temp-minibuffer-message "No completion") nil)))) @@ -1186,32 +1334,61 @@ ;;;============================================================== -;; The search status stack (and isearch window-local variables, not used). +;; The search status stack. (defun isearch-top-state () -;; (fetch-window-local-variables) (let ((cmd (car isearch-cmds))) + ;; #### Grr, this is so error-prone. If you add something to + ;; isearch-push-state, don't forget to update this. I thout I'd + ;; make a list of variables, and just do (mapcar* #'set vars + ;; values), but the (point) thing would spoil it, leaving to more + ;; complication. (setq isearch-string (car cmd) isearch-message (car (cdr cmd)) isearch-success (nth 3 cmd) isearch-forward (nth 4 cmd) isearch-other-end (nth 5 cmd) - isearch-invalid-regexp (nth 6 cmd) - isearch-wrapped (nth 7 cmd) - isearch-barrier (nth 8 cmd)) + isearch-word (nth 6 cmd) + isearch-invalid-regexp (nth 7 cmd) + isearch-wrapped (nth 8 cmd) + isearch-barrier (nth 9 cmd) + isearch-within-brackets (nth 10 cmd)) (goto-char (car (cdr (cdr cmd)))))) (defun isearch-pop-state () -;; (fetch-window-local-variables) - (setq isearch-cmds (cdr isearch-cmds)) + (pop isearch-cmds) (isearch-top-state) - ) + + ;; Make sure isearch-case-fold-search gets the correct value. FSF + ;; simply stores isearch-case-fold-search to isearch-cmds. We + ;; should probably do the same. + (isearch-fix-case) + + ;; Here, as well as in isearch-search we must deal with the point + ;; landing at an invisible area which may need unhiding. + (if (or (not (eq search-invisible 'open)) + (not isearch-hide-immediately)) + ;; If search-invisible is t, invisible text is just like any + ;; other text. If it is nil, it is always skipped and we can't + ;; land inside. In both cases, we don't need to do anything. + ;; + ;; Similarly, if isearch-hide-immediately is nil, needn't + ;; re-hide the area here, and neither can we land back into a + ;; hidden one. + nil + (when isearch-other-end + ;; This will unhide the extents. + (isearch-range-invisible (point) isearch-other-end)) + (isearch-restore-invisible-extents (point) + (or isearch-other-end (point))))) (defun isearch-push-state () - (setq isearch-cmds + (setq isearch-cmds (cons (list isearch-string isearch-message (point) - isearch-success isearch-forward isearch-other-end - isearch-invalid-regexp isearch-wrapped isearch-barrier) + isearch-success isearch-forward isearch-other-end + isearch-word + isearch-invalid-regexp isearch-wrapped isearch-barrier + isearch-within-brackets) isearch-cmds))) @@ -1222,27 +1399,41 @@ ;; Generate and print the message string. (let ((cursor-in-echo-area ellipsis) (m (concat - (isearch-message-prefix c-q-hack) + (isearch-message-prefix c-q-hack ellipsis isearch-nonincremental) isearch-message - (isearch-message-suffix c-q-hack) + (isearch-message-suffix c-q-hack ellipsis) ))) - (if c-q-hack m (display-message 'progress (format "%s" m))))) + (if c-q-hack + m + (display-message 'progress (format "%s" m))))) -(defun isearch-message-prefix (&optional c-q-hack nonincremental) +(defun isearch-message-prefix (&optional c-q-hack ellipsis nonincremental) ;; If about to search, and previous search regexp was invalid, ;; check that it still is. If it is valid now, ;; let the message we display while searching say that it is valid. - (and isearch-invalid-regexp + (and isearch-invalid-regexp ellipsis (condition-case () (progn (re-search-forward isearch-string (point) t) - (setq isearch-invalid-regexp nil)) + (setq isearch-invalid-regexp nil + isearch-within-brackets nil)) (error nil))) - ;; #### - Yo! Emacs assembles strings all over the place, they can't all - ;; be internationalized in the manner proposed below... Add an explicit - ;; call to `gettext' and have the string snarfer pluck the english - ;; strings out of the comment below. XEmacs is on a purespace diet! -Stig + ;; If currently failing, display no ellipsis. + (or isearch-success (setq ellipsis nil)) + ;; #### - ! Emacs assembles strings all over the place, they can't + ;; all be internationalized in the manner proposed below... Add an + ;; explicit call to `gettext' and have the string snarfer pluck the + ;; english strings out of the comment below. XEmacs is on a + ;; purespace diet! -Stig + + ;; The comment below is dead and buried, but it can be rebuilt if + ;; necessary. -hniksic (let ((m (concat (if isearch-success nil "failing ") - (if isearch-wrapped "wrapped ") + (if (and isearch-wrapped + (if isearch-forward + (> (point) isearch-opoint) + (< (point) isearch-opoint))) + "overwrapped " + (if isearch-wrapped "wrapped ")) (if isearch-word "word ") (if isearch-regexp "regexp ") (if nonincremental "search" "I-search") @@ -1252,14 +1443,12 @@ (aset m 0 (upcase (aref m 0))) (gettext m))) -(defun isearch-message-suffix (&optional c-q-hack) +(defun isearch-message-suffix (&optional c-q-hack ellipsis) (concat (if c-q-hack "^Q" "") (if isearch-invalid-regexp (concat " [" isearch-invalid-regexp "]") ""))) -;;;;; #### - yuck...this is soooo lame. Is this really worth 4k of purespace??? -;;; ;;;(let ((i (logior (if isearch-success 32 0) ;;; (if isearch-wrapped 16 0) ;;; (if isearch-word 8 0) @@ -1268,68 +1457,7 @@ ;;; (if isearch-forward 1 0)))) ;;; (cond ;;; ((= i 63) (gettext "Wrapped word regexp search: ")) ; 111111 -;;; ((= i 62) (gettext "Wrapped word regexp search backward: ")) ; 111110 -;;; ((= i 61) (gettext "Wrapped word regexp I-search: ")) ; 111101 -;;; ((= i 60) (gettext "Wrapped word regexp I-search backward: ")) ; 111100 -;;; ((= i 59) (gettext "Wrapped word search: ")) ; 111011 -;;; ((= i 58) (gettext "Wrapped word search backward: ")) ; 111010 -;;; ((= i 57) (gettext "Wrapped word I-search: ")) ; 111001 -;;; ((= i 56) (gettext "Wrapped word I-search backward: ")) ; 111000 -;;; ((= i 55) (gettext "Wrapped regexp search: ")) ; 110111 -;;; ((= i 54) (gettext "Wrapped regexp search backward: ")) ; 110110 -;;; ((= i 53) (gettext "Wrapped regexp I-search: ")) ; 110101 -;;; ((= i 52) (gettext "Wrapped regexp I-search backward: ")) ; 110100 -;;; ((= i 51) (gettext "Wrapped search: ")) ; 110011 -;;; ((= i 50) (gettext "Wrapped search backward: ")) ; 110010 -;;; ((= i 49) (gettext "Wrapped I-search: ")) ; 110001 -;;; ((= i 48) (gettext "Wrapped I-search backward: ")) ; 110000 -;;; ((= i 47) (gettext "Word regexp search: ")) ; 101111 -;;; ((= i 46) (gettext "Word regexp search backward: ")) ; 101110 -;;; ((= i 45) (gettext "Word regexp I-search: ")) ; 101101 -;;; ((= i 44) (gettext "Word regexp I-search backward: ")) ; 101100 -;;; ((= i 43) (gettext "Word search: ")) ; 101011 -;;; ((= i 42) (gettext "Word search backward: ")) ; 101010 -;;; ((= i 41) (gettext "Word I-search: ")) ; 101001 -;;; ((= i 40) (gettext "Word I-search backward: ")) ; 101000 -;;; ((= i 39) (gettext "Regexp search: ")) ; 100111 -;;; ((= i 38) (gettext "Regexp search backward: ")) ; 100110 -;;; ((= i 37) (gettext "Regexp I-search: ")) ; 100101 -;;; ((= i 36) (gettext "Regexp I-search backward: ")) ; 100100 -;;; ((= i 35) (gettext "Search: ")) ; 100011 -;;; ((= i 34) (gettext "Search backward: ")) ; 100010 -;;; ((= i 33) (gettext "I-search: ")) ; 100001 -;;; ((= i 32) (gettext "I-search backward: ")) ; 100000 -;;; ((= i 31) (gettext "Failing wrapped word regexp search: ")) ; 011111 -;;; ((= i 30) (gettext "Failing wrapped word regexp search backward: ")) ; 011110 -;;; ((= i 29) (gettext "Failing wrapped word regexp I-search: ")) ; 011101 -;;; ((= i 28) (gettext "Failing wrapped word regexp I-search backward: ")) ; 011100 -;;; ((= i 27) (gettext "Failing wrapped word search: ")) ; 011011 -;;; ((= i 26) (gettext "Failing wrapped word search backward: ")) ; 011010 -;;; ((= i 25) (gettext "Failing wrapped word I-search: ")) ; 011001 -;;; ((= i 24) (gettext "Failing wrapped word I-search backward: ")) ; 011000 -;;; ((= i 23) (gettext "Failing wrapped regexp search: ")) ; 010111 -;;; ((= i 22) (gettext "Failing wrapped regexp search backward: ")) ; 010110 -;;; ((= i 21) (gettext "Failing wrapped regexp I-search: ")) ; 010101 -;;; ((= i 20) (gettext "Failing wrapped regexp I-search backward: ")) ; 010100 -;;; ((= i 19) (gettext "Failing wrapped search: ")) ; 010011 -;;; ((= i 18) (gettext "Failing wrapped search backward: ")) ; 010010 -;;; ((= i 17) (gettext "Failing wrapped I-search: ")) ; 010001 -;;; ((= i 16) (gettext "Failing wrapped I-search backward: ")) ; 010000 -;;; ((= i 15) (gettext "Failing word regexp search: ")) ; 001111 -;;; ((= i 14) (gettext "Failing word regexp search backward: ")) ; 001110 -;;; ((= i 13) (gettext "Failing word regexp I-search: ")) ; 001101 -;;; ((= i 12) (gettext "Failing word regexp I-search backward: ")) ; 001100 -;;; ((= i 11) (gettext "Failing word search: ")) ; 001011 -;;; ((= i 10) (gettext "Failing word search backward: ")) ; 001010 -;;; ((= i 9) (gettext "Failing word I-search: ")) ; 001001 -;;; ((= i 8) (gettext "Failing word I-search backward: ")) ; 001000 -;;; ((= i 7) (gettext "Failing regexp search: ")) ; 000111 -;;; ((= i 6) (gettext "Failing regexp search backward: ")) ; 000110 -;;; ((= i 5) (gettext "Failing regexp I-search: ")) ; 000101 -;;; ((= i 4) (gettext "Failing regexp I-search backward: ")) ; 000100 -;;; ((= i 3) (gettext "Failing search: ")) ; 000011 -;;; ((= i 2) (gettext "Failing search backward: ")) ; 000010 -;;; ((= i 1) (gettext "Failing I-search: ")) ; 000001 +;;; ...and so on, ad nauseam... ;;; ((= i 0) (gettext "Failing I-search backward: ")) ; 000000 ;;; (t (error "Something's rotten"))))) @@ -1343,6 +1471,7 @@ (put 'isearch-repeat-backward 'isearch-command t) (put 'isearch-delete-char 'isearch-command t) (put 'isearch-help-or-delete-char 'isearch-command t) +(put 'isearch-cancel 'isearch-command t) (put 'isearch-abort 'isearch-command t) (put 'isearch-quote-char 'isearch-command t) (put 'isearch-exit 'isearch-command t) @@ -1371,6 +1500,8 @@ (put 'isearch-forward-exit-minibuffer 'isearch-command t) (put 'isearch-reverse-exit-minibuffer 'isearch-command t) (put 'isearch-nonincremental-exit-minibuffer 'isearch-command t) +(put 'isearch-yank-selection 'isearch-command t) +(put 'isearch-yank-clipboard 'isearch-command t) (put 'isearch-yank-x-selection 'isearch-command t) (put 'isearch-yank-x-clipboard 'isearch-command t) @@ -1408,11 +1539,24 @@ ;; (cond ((not (eq (current-buffer) isearch-buffer)) ;; If the buffer (likely meaning "frame") has changed, bail. - ;; This can also happen if a proc filter has popped up another - ;; buffer, which is arguably a bad thing for it to have done, - ;; but the way in which isearch would have hosed you in that - ;; case is unarguably even worse. -jwz - (isearch-done)) + ;; This can happen if the user types something into another + ;; frame. It can also happen if a proc filter has popped up + ;; another buffer, which is arguably a bad thing for it to + ;; have done, but the way in which isearch would have hosed + ;; you in that case is unarguably even worse. -jwz + (isearch-done) + + ;; `this-command' is set according to the value of + ;; `overriding-local-map', set by isearch-mode. This is + ;; wrong because that keymap makes sense only in isearch + ;; buffer. To make sure the right command is called, adjust + ;; `this-command' to the appropriate value, now that + ;; `isearch-done' has set `overriding-local-map' to nil. + + ;; FSF does similar magic in `isearch-other-meta-char', which + ;; is horribly complex. I *hope* what we do works in all + ;; cases. + (setq this-command (key-binding (this-command-keys)))) (t (isearch-maybe-frob-keyboard-macros) (if (and this-command @@ -1453,15 +1597,10 @@ ;;;======================================================== ;;; Highlighting -(defcustom isearch-highlight t - "*Whether isearch and query-replace should highlight the text which -currently matches the search-string.") - (defvar isearch-extent nil) -;; this face is initialized by x-faces.el since isearch is preloaded. -;; this face is now created in initialize-faces -;;(make-face 'isearch) +;; this face is initialized by faces.el since isearch is preloaded. +;(make-face 'isearch) (defun isearch-make-extent (begin end) (let ((x (make-extent begin end (current-buffer)))) @@ -1469,28 +1608,28 @@ ;; highlighted extents we may be passing through, since isearch, being ;; modal, is more interesting (there's nothing they could do with a ;; mouse-highlighted extent while in the midst of a search anyway). - (set-extent-priority x (1+ mouse-highlight-priority)) + (set-extent-priority x (+ mouse-highlight-priority 2)) (set-extent-face x 'isearch) (setq isearch-extent x))) (defun isearch-highlight (begin end) - (if (null isearch-highlight) + (if (null search-highlight) nil ;; make sure isearch-extent is in the current buffer - (or (extentp isearch-extent) + (or (and (extentp isearch-extent) + (extent-live-p isearch-extent)) (isearch-make-extent begin end)) (set-extent-endpoints isearch-extent begin end (current-buffer)))) -(defun isearch-dehighlight (totally) - (if (and isearch-highlight isearch-extent) - (if totally - (let ((inhibit-quit t)) - (if (extentp isearch-extent) - (delete-extent isearch-extent)) - (setq isearch-extent nil)) - (if (extentp isearch-extent) - (detach-extent isearch-extent) - (setq isearch-extent nil))))) +;; This used to have a TOTALLY flag that also deleted the extent. I +;; don't think this is necessary any longer, as isearch-highlight can +;; simply move the extent to another buffer. The IGNORED argument is +;; for the code that calls this function with an argument. --hniksic +(defun isearch-dehighlight (&optional ignored) + (and search-highlight + (extentp isearch-extent) + (extent-live-p isearch-extent) + (detach-extent isearch-extent))) ;;;======================================================== @@ -1502,33 +1641,54 @@ (isearch-fix-case) (condition-case lossage (let ((inhibit-quit nil) - (case-fold-search isearch-case-fold-search)) + (case-fold-search isearch-case-fold-search) + (retry t)) (if isearch-regexp (setq isearch-invalid-regexp nil)) - (setq isearch-success - (funcall - (cond (isearch-word - (if isearch-forward - 'word-search-forward 'word-search-backward)) - (isearch-regexp - (if isearch-forward - 're-search-forward 're-search-backward)) - (t - (if isearch-forward 'search-forward 'search-backward))) - isearch-string nil t)) + (setq isearch-within-brackets nil) + (while retry + (setq isearch-success + (funcall + (cond (isearch-word + (if isearch-forward + 'word-search-forward 'word-search-backward)) + (isearch-regexp + (if isearch-forward + 're-search-forward 're-search-backward)) + (t + (if isearch-forward 'search-forward 'search-backward))) + isearch-string nil t)) + ;; Clear RETRY unless we matched some invisible text + ;; and we aren't supposed to do that. + (if (or (eq search-invisible t) + (not isearch-success) + (bobp) (eobp) + (= (match-beginning 0) (match-end 0)) + (not (isearch-range-invisible + (match-beginning 0) (match-end 0)))) + (setq retry nil))) (setq isearch-just-started nil) - (if isearch-success - (setq isearch-other-end - (if isearch-forward (match-beginning 0) (match-end 0))))) + (when isearch-success + (setq isearch-other-end + (if isearch-forward (match-beginning 0) (match-end 0))) + (and isearch-hide-immediately + (isearch-restore-invisible-extents (match-beginning 0) + (match-end 0))))) - (quit (setq unread-command-event (character-to-event (quit-char))) + (quit (setq unread-command-events (nconc unread-command-events + (character-to-event (quit-char)))) (setq isearch-success nil)) - (invalid-regexp + (invalid-regexp (setq isearch-invalid-regexp (car (cdr lossage))) + (setq isearch-within-brackets (string-match "\\`Unmatched \\[" + isearch-invalid-regexp)) (if (string-match "\\`Premature \\|\\`Unmatched \\|\\`Invalid " isearch-invalid-regexp) - (setq isearch-invalid-regexp (gettext "incomplete input"))))) + (setq isearch-invalid-regexp (gettext "incomplete input")))) + (error + ;; stack overflow in regexp search. + (setq isearch-invalid-regexp (car (cdr lossage))))) (if isearch-success nil @@ -1548,59 +1708,79 @@ (ding nil 'isearch-failed)) (goto-char (nth 2 (car isearch-cmds))))) -;;;================================================= -;; This is called from incremental-search -;; if the first input character is the exit character. - -;; We store the search string in `isearch-string' -;; which has been bound already by `isearch-search' -;; so that, when we exit, it is copied into `search-last-string'. - +;; Replaced with isearch-edit-string. ;(defun nonincremental-search (forward regexp) -; ;; This may be broken. Anyway, it is replaced by the isearch-edit-string. -; ;; Missing features: word search option, command history. -; (setq isearch-forward forward -; isearch-regexp regexp) -; (let (char function -; inhibit-quit -; (cursor-in-echo-area t)) -; ;; Prompt assuming not word search, -; (setq isearch-message -; (if isearch-regexp -; (if isearch-forward "Regexp search: " -; "Regexp search backward: ") -; (if isearch-forward "Search: " "Search backward: "))) -; (message "%s" isearch-message) -; ;; Read 1 char and switch to word search if it is ^W. -; (setq char (read-char)) -; (if (eq char search-yank-word-char) -; (setq isearch-message (if isearch-forward "Word search: " -; "Word search backward: ")) -; ;; Otherwise let that 1 char be part of the search string. -; (setq unread-command-event (character-to-event char)) -; ) -; (setq function -; (if (eq char search-yank-word-char) -; (if isearch-forward 'word-search-forward 'word-search-backward) -; (if isearch-regexp -; (if isearch-forward 're-search-forward 're-search-backward) -; (if isearch-forward 'search-forward 'search-backward)))) -; ;; Read the search string with corrected prompt. -; (setq isearch-string (read-string isearch-message isearch-string)) -; ;; Empty means use default. -; (if (= 0 (length isearch-string)) -; (setq isearch-string search-last-string) -; ;; Set last search string now so it is set even if we fail. -; (setq search-last-string isearch-string)) -; ;; Since we used the minibuffer, we should be available for redo. -; (setq command-history -; (cons (list function isearch-string) command-history)) -; ;; Go ahead and search. -; (if search-caps-disable-folding -; (setq isearch-case-fold-search -; (no-upper-case-p isearch-string isearch-regexp))) -; (let ((case-fold-search isearch-case-fold-search)) -; (funcall function isearch-string)))) +;... + +(defun isearch-unhide-extent (extent) + ;; Store the values for the `invisible' and `intangible' + ;; properties, and then set them to nil. This way the text hidden + ;; by this extent becomes visible. + (put extent 'isearch-invisible (get extent 'invisible)) + (put extent 'isearch-intangible (get extent 'intangible)) + (put extent 'invisible nil) + (put extent 'intangible nil)) + +(defun isearch-range-invisible (beg end) + "Return t if all the text from BEG to END is invisible. +Before that, if search-invisible is `open', unhide the extents with an +`isearch-open-invisible' property." + ;; isearch-search uses this to skip the extents that are invisible, + ;; but don't have `isearch-open-invisible' set. It is unclear + ;; what's supposed to happen if only a part of [BEG, END) overlaps + ;; the extent. + (let (to-be-unhidden) + (if (map-extents + (lambda (extent ignored) + (if (and (<= (extent-start-position extent) beg) + (>= (extent-end-position extent) end)) + ;; All of the region is covered by the extent. + (if (and (eq search-invisible 'open) + (get extent 'isearch-open-invisible)) + (progn + (push extent to-be-unhidden) + nil) ; keep mapping + ;; We can't or won't unhide this extent, so we must + ;; skip the whole match. We return from map-extents + ;; immediately. + t) + ;; Else, keep looking. + nil)) + nil beg end nil 'all-extents-closed 'invisible) + ;; The whole match must be skipped. Signal it by returning t + ;; to the caller. + t + ;; If any extents need to be unhidden, unhide them. + (mapc #'isearch-unhide-extent to-be-unhidden) + ;; Will leave this assert for some time, to catch bugs. + (assert (null (intersection to-be-unhidden isearch-unhidden-extents))) + (setq isearch-unhidden-extents (nconc to-be-unhidden + isearch-unhidden-extents)) + nil))) + +(defun isearch-restore-extent (extent) + (put extent 'invisible (get extent 'isearch-invisible)) + (put extent 'intangible (get extent 'isearch-intangible)) + (remprop extent 'isearch-invisible) + (remprop extent 'isearch-intangible)) + +;; FSF calls this function `isearch-clean-overlays'. +(defun isearch-restore-invisible-extents (beg end) + (cond + ((null beg) + ;; Delete all -- this is called at the end of isearch. + (mapc #'isearch-restore-extent isearch-unhidden-extents) + (setq isearch-unhidden-extents nil)) + (t + ;; Extents that do not overlap the match area can be safely + ;; restored to their hidden state. + (setq isearch-unhidden-extents + (delete-if (lambda (extent) + (unless (extent-in-region-p extent beg end + 'all-extents-closed) + (isearch-restore-extent extent) + t)) + isearch-unhidden-extents))))) (defun isearch-no-upper-case-p (string) "Return t if there are no upper case chars in string. @@ -1611,6 +1791,18 @@ (not (string-match "\\(^\\|[^\\]\\)[A-Z]" string)))) (make-obsolete 'isearch-no-upper-case-p 'no-upper-case-p) +;; Portability functions to support various Emacs versions. + +(defun isearch-char-to-string (c) + (if (eventp c) + (make-string 1 (event-to-character c nil nil t)) + (make-string 1 c))) + +;(defun isearch-text-char-description (c) +; (isearch-char-to-string c)) + +(define-function 'isearch-text-char-description 'text-char-description) + ;; Used by etags.el and info.el (defmacro with-caps-disable-folding (string &rest body) "\ Eval BODY with `case-fold-search' let to nil if STRING contains @@ -1624,4 +1816,204 @@ (put 'with-caps-disable-folding 'lisp-indent-function 1) (put 'with-caps-disable-folding 'edebug-form-spec '(form body)) + +;;;======================================================== +;;; Advanced highlighting + +;; When active, *every* visible match for the current search string is +;; highlighted: the current one using the normal isearch match color +;; and all the others using the `isearch-secondary' face. The extra +;; highlighting makes it easier to anticipate where the cursor will +;; land each time you press C-s or C-r to repeat a pending search. +;; Only the matches visible at any point are highlighted -- when you +;; move through the buffer, the highlighting is readjusted. + +;; This is based on ideas from Bob Glickstein's `ishl' package. It +;; has been merged with XEmacs by Darryl Okahata, and then completely +;; rewritten by Hrvoje Niksic. + +;; The code makes the following assumptions about the rest of this +;; file, so be careful when modifying it. + +;; * `isearch-highlight-all-update' should get called when the search +;; string changes, or when the search advances. This is done from +;; `isearch-update'. +;; * `isearch-highlight-all-cleanup' should get called when the search +;; is done. This is performed in `isearch-done'. +;; * `isearch-string' is expected to contain the current search string +;; as entered by the user. +;; * `isearch-opoint' is expected to contain the location where the +;; current search began. +;; * the type of the current search is expected to be given by +;; `isearch-word' and `isearch-regexp'. +;; * the variable `isearch-invalid-regexp' is expected to be true iff +;; `isearch-string' is an invalid regexp. + +(defcustom isearch-highlight-all-matches search-highlight + "*Non-nil means highlight all visible matches." + :type 'boolean + :group 'isearch) + +;; We can't create this face here, as isearch.el is preloaded. +;; #### Think up a better name for this! +;(defface isearch-secondary '((t (:foreground "red3"))) +; "Face to use for highlighting all matches." +; :group 'isearch) + +(defvar isearch-highlight-extents nil) +(defvar isearch-window-start nil) +(defvar isearch-window-end nil) +;; We compare isearch-string and isearch-case-fold-search to saved +;; values for better efficiency. +(defvar isearch-highlight-last-string nil) +(defvar isearch-highlight-last-case-fold-search nil) +(defvar isearch-highlight-last-regexp nil) + +(defun isearch-delete-extents-in-range (start end) + ;; Delete all highlighting extents that overlap [START, END). + (setq isearch-highlight-extents + (delete-if (lambda (extent) + (when (extent-in-region-p extent start end) + (delete-extent extent) + t)) + isearch-highlight-extents))) + +(defun isearch-highlight-all-cleanup () + ;; Stop lazily highlighting and remove extra highlighting from + ;; buffer. + (mapc #'delete-extent isearch-highlight-extents) + (setq isearch-highlight-extents nil) + (setq isearch-highlight-all-start nil + isearch-window-end nil + isearch-highlight-last-string nil)) + +(defun isearch-highlight-all-update () + ;; Update the highlighting if necessary. This needs to check if the + ;; search string has changed, or if the window has changed position + ;; in the buffer. + (let ((need-start-over nil)) + ;; NB: we don't check for isearch-success because if the point is + ;; after the last match, the search can be unsuccessful, and yet + ;; there are things to highlight. + (cond ((not isearch-highlight-all-matches)) + ((or (equal isearch-string "") + isearch-invalid-regexp) + (isearch-highlight-all-cleanup)) + ((not (eq isearch-case-fold-search + isearch-highlight-last-case-fold-search)) + ;; This case is usually caused by search string being + ;; changed, which would be caught below, but it can also be + ;; tripped using isearch-toggle-case-fold. + (setq need-start-over t)) + ((not (eq isearch-regexp isearch-highlight-last-regexp)) + ;; Ditto for isearch-toggle-regexp. + (setq need-start-over t)) + ((equal isearch-string isearch-highlight-last-string) + ;; The search string is the same. We need to do something + ;; if our position has changed. + + ;; It would be nice if we didn't have to do this; however, + ;; window-start doesn't support a GUARANTEE flag, so we must + ;; force redisplay to get the correct valye for start and end + ;; of window. + (sit-for 0) + + ;; Check whether our location has changed. + (let ((start (window-start)) + (end (min (window-end) (point-max)))) + (cond ((and (= start isearch-window-start) + (= end isearch-window-end)) + ;; Our position is unchanged -- do nothing. + ) + ((and (> start isearch-window-start) + (> end isearch-window-end) + (<= start isearch-window-end)) + ;; We've migrated downward, but we overlap the old + ;; region. Delete the old non-overlapping extents + ;; and fill in the rest. + (isearch-delete-extents-in-range isearch-window-start start) + (isearch-highlightify-region isearch-window-end end) + (setq isearch-window-start start + isearch-window-end end)) + ((and (<= start isearch-window-start) + (<= end isearch-window-end) + (> end isearch-window-start)) + ;; We've migrated upward, but we overlap the old + ;; region. Delete the old non-overlapping extents + ;; and fill in the rest. + (isearch-delete-extents-in-range + end isearch-window-end) + (isearch-highlightify-region start isearch-window-start) + (setq isearch-window-start start + isearch-window-end end)) + (t + ;; The regions don't overlap, or they overlap in a + ;; weird way. + (setq need-start-over t))))) + (t + ;; The search string has changed. + + ;; If more input is pending, don't start over because + ;; starting over forces redisplay, and that slows down + ;; typing. + (unless (input-pending-p) + (setq need-start-over t)))) + (when need-start-over + ;; Force redisplay before removing the old extents, in order to + ;; avoid flicker. + (sit-for 0) + (isearch-highlight-all-cleanup) + (setq isearch-window-start (window-start) + isearch-window-end (min (window-end) (point-max))) + (isearch-highlightify-region isearch-window-start isearch-window-end)) + + (setq isearch-highlight-last-string isearch-string + isearch-highlight-last-case-fold-search isearch-case-fold-search + isearch-highlight-last-regexp isearch-regexp))) + +(defun isearch-highlight-advance (string forwardp) + ;; Search ahead for the next or previous match. This is the same as + ;; isearch-search, but without the extra baggage. Maybe it should + ;; be in a separate function. + (let ((case-fold-search isearch-case-fold-search)) + (funcall (cond (isearch-word (if forwardp + 'word-search-forward + 'word-search-backward)) + (isearch-regexp (if forwardp + 're-search-forward + 're-search-backward)) + (t (if forwardp + 'search-forward + 'search-backward))) + string nil t))) + +(defun isearch-highlightify-region (start end) + ;; Highlight all occurrences of isearch-string between START and + ;; END. To do this right, we have to search forward as long as + ;; there are matches that overlap [START, END), and then search + ;; backward the same way. + (save-excursion + (goto-char isearch-opoint) + (let ((lastpoint (point))) + (while (and (isearch-highlight-advance isearch-string t) + (/= lastpoint (point)) + (< (match-beginning 0) end)) + (let ((extent (make-extent (match-beginning 0) + (match-end 0)))) + (set-extent-priority extent (1+ mouse-highlight-priority)) + (put extent 'face 'isearch-secondary) + (push extent isearch-highlight-extents)) + (setq lastpoint (point)))) + (goto-char isearch-opoint) + (let ((lastpoint (point))) + (while (and (isearch-highlight-advance isearch-string nil) + (/= lastpoint (point)) + (>= (match-end 0) start)) + (let ((extent (make-extent (match-beginning 0) + (match-end 0)))) + (set-extent-priority extent (1+ mouse-highlight-priority)) + (put extent 'face 'isearch-secondary) + (push extent isearch-highlight-extents)) + (setq lastpoint (point)))))) + ;;; isearch-mode.el ends here diff -r 28d9c139be4c -r 11054d720c21 lisp/ldap.el --- a/lisp/ldap.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/ldap.el Mon Aug 13 11:26:11 2007 +0200 @@ -5,7 +5,7 @@ ;; Author: Oscar Figueiredo ;; Maintainer: Oscar Figueiredo ;; Created: Jan 1998 -;; Version: $Revision: 1.7.2.5 $ +;; Version: $Revision: 1.7.2.6 $ ;; Keywords: help comm ;; This file is part of XEmacs @@ -155,9 +155,7 @@ :type 'symbol :group 'ldap) -(defcustom ldap-coding-system (if (featurep 'mule) - 'utf-8 - nil) +(defcustom ldap-coding-system nil "*Coding system of LDAP string values. LDAP v3 specifies the coding system of strings to be UTF-8. Mule support is needed for this." @@ -395,10 +393,12 @@ (error "Invalid country string: %s" str))) (defun ldap-decode-string (str) - (decode-coding-string str ldap-coding-system)) + (if (fboundp 'decode-coding-string) + (decode-coding-string str ldap-coding-system))) (defun ldap-encode-string (str) - (encode-coding-string str ldap-coding-system)) + (if (fboundp 'encode-coding-string) + (encode-coding-string str ldap-coding-system))) (defun ldap-decode-address (str) (mapconcat 'ldap-decode-string diff -r 28d9c139be4c -r 11054d720c21 lisp/menubar-items.el --- a/lisp/menubar-items.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/menubar-items.el Mon Aug 13 11:26:11 2007 +0200 @@ -990,7 +990,7 @@ Adds `Load .emacs' button to menubar when starting up with -q." ;; by Stig@hackvan.com (cond - (init-file-user nil) + (load-user-init-file-p nil) ((file-exists-p (expand-file-name ".emacs" "~")) (add-menu-button nil ["Load .emacs" diff -r 28d9c139be4c -r 11054d720c21 lisp/modeline.el --- a/lisp/modeline.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/modeline.el Mon Aug 13 11:26:11 2007 +0200 @@ -595,13 +595,14 @@ (purecopy " ") 'global-mode-string (purecopy " %[(") - (cons modeline-minor-mode-extent (list "" 'mode-name 'minor-mode-alist)) - (cons modeline-narrowed-extent "%n") + (cons modeline-minor-mode-extent + (list (purecopy "") 'mode-name 'minor-mode-alist)) + (cons modeline-narrowed-extent (purecopy "%n")) 'modeline-process (purecopy ")%]----") - (purecopy '(line-number-mode "L%l--")) - (purecopy '(column-number-mode "C%c--")) - (purecopy '(-3 . "%p")) + (list 'line-number-mode (purecopy "L%l--")) + (list 'column-number-mode (purecopy "C%c--")) + (cons -3 (purecopy "%p")) (purecopy "-%-"))) ;;; Added for XEmacs 20.3. Provide wrapper for vc since it may not always be diff -r 28d9c139be4c -r 11054d720c21 lisp/mouse.el --- a/lisp/mouse.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/mouse.el Mon Aug 13 11:26:11 2007 +0200 @@ -84,8 +84,9 @@ "Function that is called upon by `mouse-yank' to actually insert text.") (defun mouse-consolidated-yank () - "Insert the current selection or, if there is none under X insert the X cutbuffer. -A mark is pushed, so that the inserted text lies between point and mark." + "Insert the current selection or, if there is none under X insert +the X cutbuffer. A mark is pushed, so that the inserted text lies +between point and mark." (interactive) (if (not (console-on-window-system-p)) (yank) @@ -225,9 +226,10 @@ (if (click-inside-extent-p event zmacs-region-extent) ;; okay, this is a drag (cond ((featurep 'offix) - (offix-start-drag-region event - (extent-start-position zmacs-region-extent) - (extent-end-position zmacs-region-extent))) + (offix-start-drag-region + event + (extent-start-position zmacs-region-extent) + (extent-end-position zmacs-region-extent))) ((featurep 'cde) ;; should also work with CDE (cde-start-drag-region event diff -r 28d9c139be4c -r 11054d720c21 lisp/mule/mule-cmds.el --- a/lisp/mule/mule-cmds.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/mule/mule-cmds.el Mon Aug 13 11:26:11 2007 +0200 @@ -787,6 +787,8 @@ (input-method (completing-read prompt input-method-alist nil t nil 'input-method-history default))) + (if (and input-method (symbolp input-method)) + (setq input-method (symbol-name input-method))) (if (> (length input-method) 0) input-method (if inhibit-null diff -r 28d9c139be4c -r 11054d720c21 lisp/obsolete.el --- a/lisp/obsolete.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/obsolete.el Mon Aug 13 11:26:11 2007 +0200 @@ -171,6 +171,10 @@ set Info-directory-list.") (make-obsolete-variable 'Info-default-directory-list 'Info-directory-list) +(defvar init-file-user nil + "This used to be the name of the user whose init file was read at startup.") +(make-obsolete-variable 'init-file-user 'load-user-init-file-p) + ;;;;;;;;;;;;;;;;;;;;;;;;;;;; hooks (make-compatible-variable 'lisp-indent-hook 'lisp-indent-function) @@ -242,6 +246,11 @@ (define-compatible-function-alias 'byte-code-function-p 'compiled-function-p) ;FSFmacs +(define-obsolete-function-alias 'isearch-yank-x-selection + 'isearch-yank-selection) +(define-obsolete-function-alias 'isearch-yank-x-clipboard + 'isearch-yank-clipboard) + ;; too bad there's not a way to check for aref, assq, and nconc ;; being called on the values of functions known to return keymaps, ;; or known to return vectors of events instead of strings... diff -r 28d9c139be4c -r 11054d720c21 lisp/package-get.el --- a/lisp/package-get.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/package-get.el Mon Aug 13 11:26:11 2007 +0200 @@ -180,6 +180,7 @@ (list :tag "Remote" host-name directory) )) :group 'package-get) +;;;###autoload (defcustom package-get-download-sites '( ;; North America @@ -239,6 +240,10 @@ :type 'file :group 'package-get) +(defvar package-get-user-index-filename + (paths-construct-path (list user-init-directory package-get-base-filename)) + "Name for the user-specific location of the package-get database file.") + (defcustom package-get-always-update nil "*If Non-nil always make sure we are using the latest package index (base). Otherwise respect the `force-current' argument of `package-get-require-base'." @@ -261,11 +266,16 @@ (defun package-get-download-menu () "Build the `Add Download Site' menu." (mapcar (lambda (site) - (vector (car site) - `(package-ui-add-site (quote ,(cdr site))) - :style 'toggle :selected - `(member (quote ,(cdr site)) package-get-remote))) - package-get-download-sites)) + (vector (car site) + `(if (member (quote ,(cdr site)) + package-get-remote) + (setq package-get-remote + (delete (quote ,(cdr site)) package-get-remote)) + (package-ui-add-site (quote ,(cdr site)))) + :style 'toggle + :selected `(member (quote ,(cdr site)) + package-get-remote))) + package-get-download-sites)) ;;;###autoload (defun package-get-require-base (&optional force-current) @@ -328,23 +338,21 @@ "Locate the package-get index file. Do not return remote paths if NO-REMOTE is non-nil." (or (package-get-locate-file package-get-base-filename t no-remote) - (locate-data-file package-get-base-filename) - package-get-base-filename)) - -(defvar package-get-user-package-location user-init-directory) + (if (file-exists-p package-get-user-index-filename) + package-get-user-index-filename))) (defun package-get-maybe-save-index (filename) "Offer to save the current buffer as the local package index file, if different." (let ((location (package-get-locate-index-file t))) (unless (and filename (equal filename location)) - (unless (equal (md5 (current-buffer)) - (with-temp-buffer - (insert-file-contents location) - (md5 (current-buffer)))) - (unless (file-writable-p location) - (setq location (expand-file-name package-get-base-filename - (expand-file-name "etc/" package-get-user-package-location)))) + (unless (and location + (equal (md5 (current-buffer)) + (with-temp-buffer + (insert-file-contents-literally location) + (md5 (current-buffer))))) + (unless (and location (file-writable-p location)) + (setq location package-get-user-index-filename)) (when (y-or-n-p (concat "Update package index in" location "? ")) (write-file location)))))) @@ -1001,6 +1009,10 @@ (package-get-info-prop (car this-package) 'version)))) (setq this-package (cdr this-package))))) (setq packages (cdr packages))) + (when (interactive-p) + (if found + (message "%S" found) + (message "No appropriate package found"))) found)) ;; diff -r 28d9c139be4c -r 11054d720c21 lisp/packages.el --- a/lisp/packages.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/packages.el Mon Aug 13 11:26:11 2007 +0200 @@ -84,17 +84,8 @@ (defvar last-package-load-path nil "Load path for packages last in the load path.") -(defvar package-locations - (list - (list (paths-construct-path '("~" ".xemacs" "mule-packages")) - 'early #'(lambda () (featurep 'mule))) - (list (paths-construct-path '("~" ".xemacs" "xemacs-packages")) - 'early #'(lambda () t)) - (list "site-packages" 'late #'(lambda () t)) - (list "infodock-packages" 'late #'(lambda () (featurep 'infodock))) - (list "mule-packages" 'late #'(lambda () (featurep 'mule))) - (list "xemacs-packages" 'late #'(lambda () t))) - "Locations of the various package directories. +(defun packages-compute-package-locations (user-init-directory) + "Compute locations of the various package directories. This is a list each of whose elements describes one directory. A directory description is a three-element list. The first element is either an absolute path or a subdirectory @@ -103,7 +94,16 @@ depending on the load-path segment the hierarchy is supposed to show up in. The third component is a thunk which, if it returns NIL, causes -the directory to be ignored.") +the directory to be ignored." + (list + (list (paths-construct-path (list user-init-directory "mule-packages")) + 'early #'(lambda () (featurep 'mule))) + (list (paths-construct-path (list user-init-directory "xemacs-packages")) + 'early #'(lambda () t)) + (list "site-packages" 'late #'(lambda () t)) + (list "infodock-packages" 'late #'(lambda () (featurep 'infodock))) + (list "mule-packages" 'late #'(lambda () (featurep 'mule))) + (list "xemacs-packages" 'late #'(lambda () t)))) (defun package-get-key-1 (info key) "Locate keyword `key' in list." @@ -429,7 +429,7 @@ (setq package-locations (cdr package-locations))) packages))) -(defun packages-find-packages (roots) +(defun packages-find-packages (roots package-locations) "Find the packages." (let ((envvar-value (getenv "EMACSPACKAGEPATH"))) (if envvar-value @@ -494,7 +494,7 @@ (defun packages-load-package-lisps (package-load-path base) "Load all Lisp files of a certain name along a load path. BASE is the base name of the files." - (mapc #'(lambda (dir) + (mapcar #'(lambda (dir) (let ((file-name (expand-file-name base dir))) (condition-case error (load file-name t t) @@ -513,7 +513,7 @@ (defun packages-handle-package-dumped-lisps (handle package-load-path) "Load dumped-lisp.el files along a load path. Call HANDLE on each file off definitions of PACKAGE-LISP there." - (mapc #'(lambda (dir) + (mapcar #'(lambda (dir) (let ((file-name (expand-file-name "dumped-lisp.el" dir))) (if (file-exists-p file-name) (let (package-lisp @@ -522,7 +522,7 @@ (load file-name) ;; dumped-lisp.el could have set this ... (if package-lisp - (mapc #'(lambda (base) + (mapcar #'(lambda (base) (funcall handle base)) package-lisp)))))) package-load-path)) diff -r 28d9c139be4c -r 11054d720c21 lisp/process.el --- a/lisp/process.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/process.el Mon Aug 13 11:26:11 2007 +0200 @@ -299,7 +299,7 @@ Remaining arguments are strings to give program as arguments." (apply 'start-process-internal name buffer program program-args)) -(defun open-network-stream (name buffer host service) +(defun open-network-stream (name buffer host service &optional protocol) "Open a TCP connection for a service to a host. Returns a subprocess-object to represent the connection. Input and output work as for subprocesses; `delete-process' closes it. @@ -312,8 +312,18 @@ with any buffer Third arg is name of the host to connect to, or its IP address. Fourth arg SERVICE is name of the service desired, or an integer - specifying a port number to connect to." - (open-network-stream-internal name buffer host service)) + specifying a port number to connect to. +Fifth argument PROTOCOL is a network protocol. Currently 'tcp + (Transmission Control Protocol) and 'udp (User Datagram Protocol) are + supported. When omitted, 'tcp is assumed. + +Ouput via `process-send-string' and input via buffer or filter (see +`set-process-filter') are stream-oriented. That means UDP datagrams are +not guaranteed to be sent and received in discrete packets. (But small +datagrams around 500 bytes that are not truncated by `process-send-string' +are usually fine.) Note further that UDP protocol does not guard against +lost packets." + (open-network-stream-internal name buffer host service protocol)) (defun shell-quote-argument (argument) "Quote an argument for passing as argument to an inferior shell." diff -r 28d9c139be4c -r 11054d720c21 lisp/rect.el --- a/lisp/rect.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/rect.el Mon Aug 13 11:26:11 2007 +0200 @@ -26,7 +26,7 @@ ;;; Commentary: -;; This package provides the operations on rectangles that are ocumented +;; This package provides the operations on rectangles that are documented ;; in the XEmacs Reference Manual. ;; ### NOTE: this file has been almost completely rewritten by Didier Verna @@ -86,10 +86,10 @@ ;; The replacement for `operate-on-rectangle' -- dv (defun apply-on-rectangle (function start end &rest args) - "Call FUNCTION for each line of rectangle with corners at START, END. + "Call FUNCTION for each line of rectangle with corners at START and END. FUNCTION is called with two arguments: the start and end columns of the -rectangle, plus ARGS extra arguments. Point is at the beginning of line when -the function is called." +rectangle, plus ARGS extra arguments. Point is at the beginning of line +when the function is called." (let (startcol startpt endcol endpt) (save-excursion (goto-char start) @@ -134,17 +134,17 @@ ;;;###autoload (defvar killed-rectangle nil - "Rectangle for yank-rectangle to insert.") + "Rectangle for `yank-rectangle' to insert.") ;;;###autoload (defun kill-rectangle (start end &optional fill) - "Delete the rectangle with corners at point and mark (START and END when -called from a program) and save it as the last killed one. You might prefer to -use `delete-extract-rectangle' from a program. + "Delete the region-rectangle and save it as the last killed one. +You might prefer to use `delete-extract-rectangle' from a program. -With a prefix (or a FILL) argument, also fill lines where nothing has to be +When called from a program, the rectangle's corners are START and END. +With a prefix (or FILL) argument, also fill lines where nothing has to be deleted." - (interactive "r\nP") + (interactive "*r\nP") (when buffer-read-only (setq killed-rectangle (extract-rectangle start end)) (barf-if-buffer-read-only)) @@ -152,14 +152,14 @@ ;;;###autoload (defun delete-rectangle (start end &optional fill) - "Delete (don't save) text in rectangle with corners at point and mark (START -and END when called from a program). The same range of columns is deleted in -each line starting with the line where the region begins and ending with the -line where the region ends. + "Delete the text in the region-rectangle without saving it. +The same range of columns is deleted in each line starting with the line +where the region begins and ending with the line where the region ends. -With a prefix (or a FILL) argument, also fill lines where nothing has to be +When called from a program, the rectangle's corners are START and END. +With a prefix (or FILL) argument, also fill lines where nothing has to be deleted." - (interactive "r\nP") + (interactive "*r\nP") (apply-on-rectangle 'delete-rectangle-line start end fill)) (defun delete-rectangle-line (startcol endcol fill) @@ -240,7 +240,7 @@ ;;;###autoload (defun yank-rectangle () "Yank the last killed rectangle with upper left corner at point." - (interactive) + (interactive "*") (insert-rectangle killed-rectangle)) ;; This function is untouched --dv @@ -268,14 +268,12 @@ ;;;###autoload (defun open-rectangle (start end &optional fill) - "Blank out rectangle with corners at point and mark (START and END when -called from a program), shifting text right. The text previously in the region -is not overwritten by the blanks, but instead winds up to the right of the -rectangle. + "Blank out the region-rectangle, shifting text right. -With a prefix (or a FILL) argument, fill with blanks even if there is no text +When called from a program, the rectangle's corners are START and END. +With a prefix (or FILL) argument, fill with blanks even if there is no text on the right side of the rectangle." - (interactive "r\nP") + (interactive "*r\nP") (apply-on-rectangle 'open-rectangle-line start end fill) (goto-char start)) @@ -289,11 +287,12 @@ ;;;###autoload (defun string-rectangle (start end string) - "Insert STRING on each line of the rectangle with corners at point and mark -(START and END when called from a program), shifting text right. The left edge -of the rectangle specifies the column for insertion. This command does not -delete or overwrite any existing text." - (interactive "r\nsString rectangle: ") + "Insert STRING on each line of the region-rectangle, shifting text right. +The left edge of the rectangle specifies the column for insertion. This +command does not delete or overwrite any existing text. + +When called from a program, the rectangle's corners are START and END." + (interactive "*r\nsString rectangle: ") (apply-on-rectangle 'string-rectangle-line start end string)) (defun string-rectangle-line (startcol endcol string) @@ -302,13 +301,13 @@ ;;;###autoload (defun clear-rectangle (start end &optional fill) - "Blank out the rectangle with corners at point and mark (START and END when -called from a program). The text previously in the region is overwritten with -blanks. + "Blank out the region-rectangle. +The text previously in the region is overwritten with blanks. -With a prefix (or a FILL) argument, also fill with blanks the parts of the +When called from a program, the rectangle's corners are START and END. +With a prefix (or FILL) argument, also fill with blanks the parts of the rectangle which were empty." - (interactive "r\nP") + (interactive "*r\nP") (apply-on-rectangle 'clear-rectangle-line start end fill)) (defun clear-rectangle-line (startcol endcol fill) diff -r 28d9c139be4c -r 11054d720c21 lisp/replace.el --- a/lisp/replace.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/replace.el Mon Aug 13 11:26:11 2007 +0200 @@ -679,6 +679,7 @@ ;; Loop finding occurrences that perhaps should be replaced. (while (and keep-going (not (eobp)) + (or (null limit) (< (point) limit)) (let ((case-fold-search qr-case-fold-search)) (funcall search-function search-string limit)) ;; If the search string matches immediately after @@ -688,7 +689,8 @@ (and regexp-flag (eq lastrepl (match-beginning 0)) (not match-again))) - (if (eobp) + (if (or (eobp) + (and limit (>= (point) limit))) nil ;; Don't replace the null string ;; right after end of previous replacement. diff -r 28d9c139be4c -r 11054d720c21 lisp/select.el --- a/lisp/select.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/select.el Mon Aug 13 11:26:11 2007 +0200 @@ -66,10 +66,17 @@ (defun yank-clipboard-selection () "Insert the current Clipboard selection at point." (interactive "*") - (case (device-type (selected-device)) - (x (x-yank-clipboard-selection)) - (mswindows (mswindows-paste-clipboard)) - (otherwise nil))) + (when (console-on-window-system-p) + (setq last-command nil) + (setq this-command 'yank) ; so that yank-pop works. + (let ((clip (get-clipboard))) + (or clip (error "there is no clipboard selection")) + (push-mark) + (insert clip)))) + +(defun get-clipboard () + "Return text pasted to the clipboard." + (get-selection 'CLIPBOARD)) (define-device-method get-cutbuffer "Return the value of one of the cut buffers. @@ -178,13 +185,18 @@ (setq lost-selection-hooks 'dehilight-selection) (defun own-clipboard (string) - "Paste the given string to the X Clipboard." + "Paste the given string to the window system Clipboard." (own-selection string 'CLIPBOARD)) (defun disown-selection (&optional secondary-p) "Assuming we own the selection, disown it. With an argument, discard the secondary selection instead of the primary selection." - (disown-selection-internal (if secondary-p 'SECONDARY 'PRIMARY))) + (disown-selection-internal (if secondary-p 'SECONDARY 'PRIMARY)) + (when (and selection-sets-clipboard + (or (not secondary-p) + (eq secondary-p 'PRIMARY) + (eq secondary-p 'CLIPBOARD))) + (disown-selection-internal 'CLIPBOARD))) ;; from x-init.el ;; selections and active regions diff -r 28d9c139be4c -r 11054d720c21 lisp/setup-paths.el --- a/lisp/setup-paths.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/setup-paths.el Mon Aug 13 11:26:11 2007 +0200 @@ -42,10 +42,14 @@ "Depth of load-path searches in core Lisp paths.") (defvar paths-default-info-directories - (list (paths-construct-path '("usr" "local" "info") - (char-to-string directory-sep-char)) - (paths-construct-path '("usr" "info") - (char-to-string directory-sep-char))) + (mapcar (function + (lambda (dirlist) + (paths-construct-path + dirlist (char-to-string directory-sep-char)))) + '(("usr" "local" "info") + ("usr" "info") + ("usr" "local" "share" "info") + ("usr" "share" "info"))) "Directories appended to the end of the info path by default.") (defun paths-find-site-lisp-directory (roots) @@ -69,7 +73,7 @@ (defun paths-find-module-directory (roots) "Find the main modules directory of the XEmacs hierarchy." (paths-find-architecture-directory roots "modules" - configure-module-directory)) + nil configure-module-directory)) (defun paths-construct-load-path (roots early-package-load-path late-package-load-path last-package-load-path @@ -137,7 +141,7 @@ (defun paths-find-doc-directory (roots) "Find the documentation directory." - (paths-find-architecture-directory roots "lib-src")) + (paths-find-architecture-directory roots "lib-src" nil configure-doc-directory)) (defun paths-find-lock-directory (roots) "Find the lock directory." @@ -158,7 +162,8 @@ (defun paths-find-exec-directory (roots) "Find the binary directory." - (paths-find-architecture-directory roots "lib-src" configure-exec-directory)) + (paths-find-architecture-directory roots "lib-src" + nil configure-exec-directory)) (defun paths-construct-exec-path (roots exec-directory early-packages late-packages last-packages) diff -r 28d9c139be4c -r 11054d720c21 lisp/simple.el --- a/lisp/simple.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/simple.el Mon Aug 13 11:26:11 2007 +0200 @@ -2656,20 +2656,23 @@ (if (save-excursion (skip-chars-backward " \t") (= (point) fill-point)) + ;; 1999-09-17 hniksic: turn off Kinsoku until + ;; it's debugged. + (indent-new-comment-line) ;; 97/3/14 jhod: Kinsoku processing - ;(indent-new-comment-line) - (let ((spacep (memq (char-before (point)) '(?\ ?\t)))) - (funcall comment-line-break-function) - ;; if user type space explicitly, leave SPC - ;; even if there is no WAN. - (if spacep - (save-excursion - (goto-char fill-point) - ;; put SPC except that there is SPC - ;; already or there is sentence end. - (or (memq (char-after (point)) '(?\ ?\t)) - (fill-end-of-sentence-p) - (insert ?\ ))))) +; ;(indent-new-comment-line) +; (let ((spacep (memq (char-before (point)) '(?\ ?\t)))) +; (funcall comment-line-break-function) +; ;; if user type space explicitly, leave SPC +; ;; even if there is no WAN. +; (if spacep +; (save-excursion +; (goto-char fill-point) +; ;; put SPC except that there is SPC +; ;; already or there is sentence end. +; (or (memq (char-after (point)) '(?\ ?\t)) +; (fill-end-of-sentence-p) +; (insert ?\ ))))) (save-excursion (goto-char fill-point) (funcall comment-line-break-function))) diff -r 28d9c139be4c -r 11054d720c21 lisp/startup.el --- a/lisp/startup.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/startup.el Mon Aug 13 11:26:11 2007 +0200 @@ -104,18 +104,21 @@ (defvar emacs-roots nil "List of plausible roots of the XEmacs hierarchy.") -(defvar init-file-user nil - "Identity of user whose `.emacs' file is or was read. -The value is nil if no init file is being used; otherwise, it may be either -the null string, meaning that the init file was taken from the user that -originally logged in, or it may be a string containing a user's name. +(defvar user-init-directory-base ".xemacs" + "Base of directory where user-installed init files may go.") + +(defvar user-init-file-base (cond + ((eq system-type 'ms-dos) "_emacs") + (t ".emacs")) + "Base of init file.") -In either of the latter cases, `(concat \"~\" init-file-user \"/\")' -evaluates to the name of the directory in which the `.emacs' file was -searched for. +(defvar user-init-directory + (file-name-as-directory + (paths-construct-path (list "~" user-init-directory-base))) + "Directory where user-installed init files may go.") -Setting `init-file-user' does not prevent Emacs from loading -`site-start.el'. The only way to do that is to use `--no-site-file'.") +(defvar load-user-init-file-p t + "Non-nil if XEmacs should load the user's init file.") ;; #### called `site-run-file' in FSFmacs @@ -226,7 +229,11 @@ startup. Also implies `-vanilla'. -vanilla Equivalent to -q -no-site-file -no-early-packages. -q Same as -no-init-file. + -user-init-file Use as init file. + -user-init-directory use as init directory. -user Load user's init file instead of your own. + Equivalent to -user-init-file ~/.emacs + -user-init-directory ~/.xemacs/ -u Same as -user.\n") (let ((l command-switch-alist) (insert (lambda (&rest x) @@ -396,6 +403,7 @@ (if (null emacs-roots) (startup-find-roots-warning) (startup-setup-paths emacs-roots + user-init-directory inhibit-early-packages inhibit-site-lisp debug-paths)) @@ -491,12 +499,7 @@ ;; (standard-display-european t) ;; (require 'iso-syntax))) - ;; Figure out which user's init file to load, - ;; either from the environment or from the options. - (setq init-file-user (if (noninteractive) nil (user-login-name))) - ;; If user has not done su, use current $HOME to find .emacs. - (and init-file-user (string= init-file-user (user-real-login-name)) - (setq init-file-user "")) + (setq load-user-init-file-p (not (noninteractive))) ;; Allow (at least) these arguments anywhere in the command line (let ((new-args nil) @@ -506,7 +509,7 @@ (cond ((or (string= arg "-q") (string= arg "-no-init-file")) - (setq init-file-user nil)) + (setq load-user-init-file-p nil)) ((string= arg "-no-site-file") (setq site-start-file nil)) ((or (string= arg "-no-early-packages") @@ -517,11 +520,21 @@ ;; Some work on this one already done in emacs.c. (string= arg "-no-autoloads") (string= arg "--no-autoloads")) - (setq init-file-user nil + (setq load-user-init-file-p nil site-start-file nil)) + ((string= arg "-user-init-file") + (setq user-init-file (pop args))) + ((string= arg "-user-init-directory") + (setq user-init-directory (file-name-as-directory (pop args)))) ((or (string= arg "-u") - (string= arg "-user")) - (setq init-file-user (pop args))) + (string= arg "-user")) + (let* ((user (pop args)) + (home-user (concat "~" user))) + (setq user-init-file + (paths-construct-path (list home-user user-init-file-base))) + (setq user-init-directory + (file-name-as-directory + (paths-construct-path (list home-user user-init-directory-base)))))) ((string= arg "-debug-init") (setq init-file-debug t)) ((string= arg "-unmapped") @@ -533,7 +546,9 @@ (while args (push (pop args) new-args))) (t (push arg new-args)))) - + + (setq init-file-user (and load-user-init-file-p "")) + (nreverse new-args))) (defconst initial-scratch-message "\ @@ -618,43 +633,18 @@ (setq term (substring term 0 hyphend)) (setq term nil)))))) -(defconst user-init-directory "/.xemacs/" - "Directory where user-installed packages may go.") -(define-obsolete-variable-alias - 'emacs-user-extension-dir - 'user-init-directory) - -(defun load-user-init-file (init-file-user) +(defun load-user-init-file () "This function actually reads the init file, .emacs." - (when init-file-user -;; purge references to init.el and options.el -;; convert these to use paths-construct-path for eventual migration to init.el -;; needs to be converted when idiom for constructing "~user" paths is created -; (setq user-init-file -; (paths-construct-path (list (concat "~" init-file-user) -; user-init-directory -; "init.el"))) -; (unless (file-exists-p (expand-file-name user-init-file)) - (setq user-init-file - (paths-construct-path (list (concat "~" init-file-user) - (cond - ((eq system-type 'ms-dos) "_emacs") - (t ".emacs"))))) -; ) - (load user-init-file t t t) -;; This should not be loaded since custom stuff currently goes into .emacs -; (let ((default-custom-file -; (paths-construct-path (list (concat "~" init-file-user) -; user-init-directory -; "options.el"))) -; (when (string= custom-file default-custom-file) -; (load default-custom-file t t))) - (unless inhibit-default-init - (let ((inhibit-startup-message nil)) - ;; Users are supposed to be told their rights. - ;; (Plus how to get help and how to undo.) - ;; Don't you dare turn this off for anyone except yourself. - (load "default" t t))))) + (if (not user-init-file) + (setq user-init-file + (paths-construct-path (list "~" user-init-file-base)))) + (load user-init-file t t t) + (unless inhibit-default-init + (let ((inhibit-startup-message nil)) + ;; Users are supposed to be told their rights. + ;; (Plus how to get help and how to undo.) + ;; Don't you dare turn this off for anyone except yourself. + (load "default" t t)))) ;;; Load user's init file and default ones. (defun load-init-file () @@ -675,12 +665,13 @@ (debug-on-error-initial (if (eq init-file-debug t) 'startup init-file-debug))) (let ((debug-on-error debug-on-error-initial)) - (if init-file-debug + (if (and load-user-init-file-p init-file-debug) ;; Do this without a condition-case if the user wants to debug. - (load-user-init-file init-file-user) + (load-user-init-file) (condition-case error (progn - (load-user-init-file init-file-user) + (if load-user-init-file-p + (load-user-init-file)) (setq init-file-had-error nil)) (error (message "Error in init file: %s" (error-message-string error)) @@ -1075,7 +1066,8 @@ ;; don't let /tmp_mnt/... get into the load-path or exec-path. (abbreviate-file-name invocation-directory))) -(defun startup-setup-paths (roots &optional +(defun startup-setup-paths (roots user-init-directory + &optional inhibit-early-packages inhibit-site-lisp debug-paths) "Setup all the various paths. @@ -1090,7 +1082,9 @@ early)) (setq late-packages late) (setq last-packages last)) - (packages-find-packages roots)) + (packages-find-packages + roots + (packages-compute-package-locations user-init-directory))) (setq early-package-load-path (packages-find-package-load-path early-packages)) (setq late-package-load-path (packages-find-package-load-path late-packages)) diff -r 28d9c139be4c -r 11054d720c21 lisp/subr.el --- a/lisp/subr.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/subr.el Mon Aug 13 11:26:11 2007 +0200 @@ -223,6 +223,12 @@ The value of this variable may be buffer-local. The buffer about to be killed is current when this hook is run.") +;; called by Frecord_buffer() +(defvar record-buffer-hook nil + "Function or functions to be called when a buffer is recorded. +The value of this variable may be buffer-local. +The buffer being recorded is passed as an argument to the hook.") + ;; in C in FSFmacs (defvar kill-emacs-hook nil "Function or functions to be called when `kill-emacs' is called, @@ -239,6 +245,22 @@ (define-function 'rplaca 'setcar) (define-function 'rplacd 'setcdr) +(defun copy-symbol (symbol &optional copy-properties) + "Return a new uninterned symbol with the same name as SYMBOL. +If COPY-PROPERTIES is non-nil, the new symbol will have a copy of +SYMBOL's value, function, and property lists." + (let ((new (make-symbol (symbol-name symbol)))) + (when copy-properties + ;; This will not copy SYMBOL's chain of forwarding objects, but + ;; I think that's OK. Callers should not expect such magic to + ;; keep working in the copy in the first place. + (and (boundp symbol) + (set new (symbol-value symbol))) + (and (fboundp symbol) + (fset new (symbol-function symbol))) + (setplist new (copy-list (symbol-plist symbol)))) + new)) + ;;;; String functions. ;; XEmacs @@ -569,9 +591,6 @@ (interactive) nil) -(define-function 'mapc-internal 'mapc) -(make-obsolete 'mapc-internal 'mapc) - (define-function 'eval-in-buffer 'with-current-buffer) (make-obsolete 'eval-in-buffer 'with-current-buffer) @@ -632,13 +651,17 @@ The arguments OLD-END and OLD-BUFFER are supported for backward compatibility with pre-21.2 XEmacsen times when arguments to this function were (buffer-string &optional START END BUFFER)." - (if (or (null buffer) - (bufferp buffer) - (stringp buffer)) - ;; The new way - (buffer-substring nil nil buffer) - ;; The old way - (buffer-substring buffer old-end old-buffer))) + (cond + ((or (stringp buffer) (bufferp buffer)) + ;; Most definitely the new way. + (buffer-substring nil nil buffer)) + ((or (stringp old-buffer) (bufferp old-buffer) + (natnump buffer) (natnump old-end)) + ;; Definitely the old way. + (buffer-substring buffer old-end old-buffer)) + (t + ;; Probably the old way. + (buffer-substring buffer old-end old-buffer)))) ;; This was not present before. I think Jamie had some objections ;; to this, so I'm leaving this undefined for now. --ben diff -r 28d9c139be4c -r 11054d720c21 lisp/very-early-lisp.el --- a/lisp/very-early-lisp.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/very-early-lisp.el Mon Aug 13 11:26:11 2007 +0200 @@ -32,8 +32,8 @@ ;;; Code: -;;; Macros from Michael Sperber to replace read-time Lisp reader macros #-, #+ -;;; ####fixme duplicated in make-docfile.el and update-elc.el +;;; Intended replacement for read-time Lisp reader macros #-, #+ + (defmacro assemble-list (&rest components) "Assemble a list from COMPONENTS. This is a poor man's backquote: @@ -55,17 +55,17 @@ "Insert STUFF as a list element if FEATURE is a loaded feature. This is intended for use as a component of ASSEMBLE-LIST." (list 'splice - (if (featurep feature) - (list 'list stuff) - '()))) + (list 'if (list 'featurep (list 'quote feature)) + (list 'list stuff) + '()))) (defmacro unless-feature (feature stuff) "Insert STUFF as a list element if FEATURE is NOT a loaded feature. This is intended for use as a component of ASSEMBLE-LIST." (list 'splice - (if (featurep feature) - '() - (list 'list stuff)))) + (list 'if (list 'featurep (list 'quote feature)) + '() + (list 'list stuff)))) (provide 'very-early-lisp) diff -r 28d9c139be4c -r 11054d720c21 lisp/wid-edit.el --- a/lisp/wid-edit.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/wid-edit.el Mon Aug 13 11:26:11 2007 +0200 @@ -1935,16 +1935,11 @@ (console-on-window-system-p)) (unless gui-glyphs (let* ((gui-button-shadow-thickness 1) - (gui (make-gui-button tag 'widget-gui-action widget))) - (setq - gui-glyphs - (list - (make-glyph `(,(nth 0 (aref gui 1)) [string :data ,text])) - (make-glyph `(,(nth 1 (aref gui 1)) [string :data ,text])) - (make-glyph `(,(nth 2 (aref gui 1)) [string :data ,text])))) + (gui (make-glyph + (make-gui-button tag 'widget-gui-action widget)))) + (setq gui-glyphs gui) (laxputf widget-push-button-cache tag gui-glyphs))) - (widget-glyph-insert-glyph - widget (nth 0 gui-glyphs) (nth 1 gui-glyphs) (nth 2 gui-glyphs))) + (widget-glyph-insert-glyph widget gui-glyphs)) (t (insert text))))) diff -r 28d9c139be4c -r 11054d720c21 lisp/winnt.el --- a/lisp/winnt.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/winnt.el Mon Aug 13 11:26:11 2007 +0200 @@ -39,11 +39,14 @@ ;; #### Oh if we had an alist of shells and their command switches. (setq shell-command-switch "/c") -;; For appending suffixes to directories and files in shell completions. -(defun nt-shell-mode-hook () - (setq comint-completion-addsuffix '("\\" . " ") - comint-process-echoes t)) -(add-hook 'shell-mode-hook 'nt-shell-mode-hook) +;; For appending suffixes to directories and files in shell +;; completions. This screws up cygwin users so we leave it out for +;; now. Uncomment this if you only ever want to use cmd. + +;(defun nt-shell-mode-hook () +; (setq comint-completion-addsuffix '("\\" . " ") +; comint-process-echoes t)) +;(add-hook 'shell-mode-hook 'nt-shell-mode-hook) ;; Use ";" instead of ":" as a path separator (from files.el). (setq path-separator ";") diff -r 28d9c139be4c -r 11054d720c21 lisp/x-select.el --- a/lisp/x-select.el Mon Aug 13 11:25:03 2007 +0200 +++ b/lisp/x-select.el Mon Aug 13 11:26:11 2007 +0200 @@ -50,6 +50,9 @@ 'select-make-extent-for-selection) (define-obsolete-function-alias 'x-cut-copy-clear-internal 'cut-copy-clear-internal) (define-obsolete-function-alias 'x-get-selection 'get-selection) +(define-obsolete-function-alias 'x-get-clipboard 'get-clipboard) +(define-obsolete-function-alias 'x-yank-clipboard-selection + 'yank-clipboard-selection) (define-obsolete-function-alias 'x-disown-selection-internal 'disown-selection-internal) @@ -57,10 +60,6 @@ "Return text selected from some X window." (get-selection 'SECONDARY)) -(defun x-get-clipboard () - "Return text pasted to the clipboard." - (get-selection 'CLIPBOARD)) - (defun x-own-secondary-selection (selection &optional type) "Make a secondary X Selection of the given argument. The argument may be a string or a cons of two markers (in which case the selection is considered to @@ -154,19 +153,6 @@ (x-store-cutbuffer-internal 'CUT_BUFFER0 string)))) -;;; Random utility functions - -(defun x-yank-clipboard-selection () - "Insert the current Clipboard selection at point." - (interactive "*") - (setq last-command nil) - (setq this-command 'yank) ; so that yank-pop works. - (let ((clip (x-get-clipboard))) - (or clip (error "there is no clipboard selection")) - (push-mark) - (insert clip))) - - ;FSFmacs (provide 'select) ;;; x-select.el ends here. diff -r 28d9c139be4c -r 11054d720c21 lwlib/ChangeLog --- a/lwlib/ChangeLog Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/ChangeLog Mon Aug 13 11:26:11 2007 +0200 @@ -1,3 +1,217 @@ +1999-11-10 XEmacs Build Bot + + * XEmacs 21.2.20 is released + +1999-09-09 Andy Piper + + * xlwtabs.c: updated tabs widget from Ed Falk. + * xlwtabs.h: ditto. + * xlwtabsP.h: ditto. + +1999-09-22 Martin Buchholz + + * lwlib-internal.h: + * lwlib-utils.h: + Move declaration of destroy_all_children from lwlib-internal.h to + lwlib-utils.h, where it belongs. + +1999-09-21 Andy Piper + + * lwlib-Xm.c (xm_update_label): don't clobber pixmap type labels + with text. + +1999-09-22 Martin Buchholz + + * xlwtabs.c: Fix C++ compilability. + +1999-09-18 Andy Piper + + * xlwtabs.c: Put in tabs sync because clipping should fix useability + problems. + +1999-09-13 Andy Piper + + * xlwtabs.c: Back out tabs sync because of reported useability + problems. + +1999-09-09 Andy Piper + + * xlwtabs.c: updated tabs widget from Ed Falk. + * xlwtabs.h: ditto. + * xlwtabsP.h: ditto. + * xlwgcs.c: ditto. + * xlwgcs.h: ditto. + +1999-09-03 Martin Buchholz + + * xlwgauge.c: Ansify. + Include to get prototype for atoi(). + (GaugeSelect): Call GaugeExpose with the right number of args. + (GaugeLoseSel): Call GaugeExpose with the right number of args. + (GaugeConvert): This is a XtConvertSelectionProc, + so 5th parameter must be of type XtPointer, not XPointer. + (GaugeGetValue): This is a XtTimerCallbackProc, + so 2nd parameter must be of type XtIntervalId *, not XtIntervalId. + + +1999-09-01 Martin Buchholz + + * lwlib.c (free_widget_value_contents): Use proper type for cast. + + * xlwradio.c: Use function prototypes everywhere. + * xlwcheckbox.c: + * xlwradio.c: + * xlwradioP.h: Move declarations of non-static functions defined + in xlwradio.c into xlwradioP.h. + +1999-09-02 Andy Piper + + * xlwgcs.c: include xmu.h + +1999-09-01 Andy Piper + + * xlwgauge.c: rearrange headers yet again. + * xlwcheckbox.c: ditto. + * xlwradio.c: ditto. + * xlwtabs.c: ditto. + +1999-09-01 Andy Piper + + * xlwgauge.c: use xmu.h + * xlwcheckbox.c: ditto. + * xlwradio.c: ditto. + +1999-08-31 Andy Piper + + * xlwtabs.c: + * xlwgcs.c: + * xlwradio.c: + * xlwcheckbox.c: + * xlwgauge.c: Fix for losing systems without Xmu. + +1999-08-31 Andy Piper + + * lwlib-Xm.c (xm_update_one_widget): fix for AIX compiler lossage. + +1999-08-30 Andy Piper + + * lwlib.c (free_widget_value_contents): be more precise about + freeing user defined args. + + * lwlib-Xaw.c (xaw_update_one_widget): make sure we use val not + its contents for hierarchies one deep. + +1999-08-29 Andy Piper + + * xlwtabs.c: temporary fixes pending a new release. + * xlwtabsP.h: ditto. + + * lwlib-Xm.c (xm_update_one_widget): update user defined args. + (xm_create_label): set args after creation as well as before. + + * lwlib-Xlw.c (xlw_create_tab_control): orient tabs horizontally. + (xlw_update_tab_control): actually update the children rather than + the parent. + + * lwlib-Xaw.c (xaw_update_one_widget): update user defined args. + (xaw_create_label): set args after creation as well as before. + +1999-08-23 Andy Piper + + * lwlib-Xm.c (xm_update_label): don't concatenate value to itself. + + * lwlib-Xm.c (xm_create_label_field): new function for creating labels. + (xm_creation_table): use it. + + * lwlib-Xaw.c (xaw_create_label_field): new function for creating labels. + (xaw_creation_table): use it. + +1999-08-16 Andy Piper + + * lwlib.h: declare free_widget_value_tree. + + * lwlib.c (free_widget_value_tree): make non-static. + + * lwlib-Xm.c (xm_update_label): free val_string when updating. + +1999-08-04 Andy Piper + + * lwlib-Xm.c (mark_dead_instance_destroyed): change so that its + defined for widgets. + (xm_nosel_callback): ditto. + + * xlwtabsP.h: sync with 1.5. + + * xlwtabs.c: sync with 1.18. + +1999-07-28 Andy Piper + + * xlwtabs.c: new lucid tabs widget from Ed Falk. + * xlwtabs.h: ditto. + * xlwtabsP.h: ditto. + * xlwgcs.c: GC manipulation for tab widgets. + * xlwgcs.h: ditto. + + * xlwgauge.c: new athena gauge widget from Ed Falk. + * xlwgauge.h: ditto. + * xlwgaugeP.h: ditto. + + * xlwradio.c: new athena radio widget from Ed Falk. + * xlwradio.h: ditto. + * xlwradioP.h: ditto. + + * xlwcheckbox.c: new athena checkbox widget from Ed Falk. + * xlwcheckbox.h: ditto. + * xlwcheckboxP.h: ditto. + + * lwlib-utils.c (destroy_all_children): moved from lwlib-Xm.c. + + * lwlib-internal.h: declare destroy_all_children. + + * lwlib-config.c: add widget checks. + + * lwlib-Xm.h: declare xm_create_label; + + * lwlib-Xm.c (destroy_all_children): move to lwlib-utils.c. + (xm_update_label): enable for widgets. + (xm_update_one_widget): ditto. + (xm_create_button): rename in line with lwlib-Xaw.c + (xm_create_progress): ditto. + (xm_create_text_field): ditto. + (xm_create_combo_box): ditto. + (xm_create_label): new function. + (xm_creation_table): rename widget creation functions. + (xm_destroy_instance): enable for widgets. + (xm_generic_callback): ditto. + (xm_generic_callback): ditto. + + * lwlib-Xlw.c (xlw_tab_control_callback): new function. a special + callback that calls the correct function depending on what tab is + selected. + (xlw_create_tab_control): new function. + (build_tabs_in_widget): new function. puts tabs in a tab widget, + uses Xaw or Xm depending on how XEmacs was compiled. + (xlw_update_tab_control): update the resources for each + tab. optionally rebuild the contents of the tab widget. + (xlw_creation_table): add tab widget creation function. + (lw_lucid_widget_p): add tab widget. + (xlw_update_one_widget): ditto. + + * lwlib-Xaw.h: declare xaw_create_label; + + * lwlib-Xaw.c (lw_xaw_widget_p): add widgets classes. + (xaw_update_one_widget): ditto. + (xaw_update_one_value): add code from the Xm version. + (xaw_generic_callback): add Xm hack for setting command + states. beef up lookup of call data. + (xaw_create_button): new function. + (xaw_create_label): new function for use by tab widget. + (xaw_create_progress): new function. + (xaw_create_text_field): new function. + (xaw_creation_table): add new widget type creation functions. + + * Makefile.in.in: add dependencies for new lw widgets. + 1999-07-30 XEmacs Build Bot * XEmacs 21.2.19 is released diff -r 28d9c139be4c -r 11054d720c21 lwlib/Makefile.in.in --- a/lwlib/Makefile.in.in Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/Makefile.in.in Mon Aug 13 11:26:11 2007 +0200 @@ -95,11 +95,18 @@ ## Following correct as of 19980312 -lwlib-Xaw.o: $(CONFIG_H) lwlib-Xaw.h lwlib-internal.h lwlib.h xlwmenu.h -lwlib-Xlw.o: $(CONFIG_H) lwlib-Xlw.h lwlib-internal.h lwlib.h xlwmenu.h xlwscrollbar.h +lwlib-Xaw.o: $(CONFIG_H) lwlib-Xaw.h lwlib-internal.h lwlib.h xlwmenu.h xlwradio.h \ +xlwgauge.h xlwcheckbox.h +lwlib-Xlw.o: $(CONFIG_H) lwlib-Xlw.h lwlib-internal.h lwlib.h xlwmenu.h xlwscrollbar.h \ +xlwtabs.h xlwgcs.h lwlib-Xm.o: $(CONFIG_H) lwlib-Xm.h lwlib-internal.h lwlib-utils.h lwlib.h xlwmenu.h lwlib-config.o: $(CONFIG_H) lwlib.h xlwmenu.h lwlib-utils.o: $(CONFIG_H) lwlib-utils.h lwlib.o: $(CONFIG_H) lwlib-Xaw.h lwlib-Xlw.h lwlib-Xm.h lwlib-internal.h lwlib-utils.h lwlib.h xlwmenu.h xlwmenu.o: $(CONFIG_H) lwlib.h xlwmenu.h xlwmenuP.h xlwscrollbar.o: $(CONFIG_H) xlwscrollbar.h xlwscrollbarP.h +xlwtabs.o: $(CONFIG_H) xlwtabs.h xlwtabsP.h +xlwradio.o: $(CONFIG_H) xlwradio.h xlwradioP.h +xlwcheckbox.o: $(CONFIG_H) xlwcheckbox.h xlwcheckboxP.h +xlwgauge.o: $(CONFIG_H) xlwgauge.h xlwgaugeP.h +xlwgcs.o: $(CONFIG_H) xlwgcs.h diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib-Xaw.c --- a/lwlib/lwlib-Xaw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib-Xaw.c Mon Aug 13 11:26:11 2007 +0200 @@ -41,7 +41,15 @@ #include #include #endif - +#ifdef LWLIB_WIDGETS_ATHENA +#include +#include "xlwradio.h" +#include "xlwcheckbox.h" +#include "xlwgauge.h" +#ifndef NEED_MOTIF +#include +#endif +#endif #include static void xaw_generic_callback (Widget, XtPointer, XtPointer); @@ -57,6 +65,14 @@ #ifdef LWLIB_DIALOGS_ATHENA || XtIsSubclass (widget, dialogWidgetClass) #endif +#ifdef LWLIB_WIDGETS_ATHENA + || XtIsSubclass (widget, labelWidgetClass) + || XtIsSubclass (widget, toggleWidgetClass) + || XtIsSubclass (widget, gaugeWidgetClass) +#if 0 + || XtIsSubclass (widget, textWidgetClass) +#endif +#endif ); } @@ -110,6 +126,9 @@ xaw_update_one_widget (widget_instance *instance, Widget widget, widget_value *val, Boolean deep_p) { + if (val->nargs) + XtSetValues (widget, val->args, val->nargs); + if (0) ; #ifdef LWLIB_SCROLLBARS_ATHENA @@ -125,6 +144,16 @@ XtSetArg (al [0], XtNlabel, val->contents->value); XtSetValues (widget, al, 1); } +#endif /* LWLIB_DIALOGS_ATHENA */ +#ifdef LWLIB_WIDGETS_ATHENA + else if (XtClass (widget) == labelWidgetClass) + { + Arg al [1]; + XtSetArg (al [0], XtNlabel, val->value); + XtSetValues (widget, al, 1); + } +#endif /* LWLIB_WIDGETS_ATHENA */ +#if defined (LWLIB_DIALOGS_ATHENA) || defined (LWLIB_WIDGETS_ATHENA) else if (XtIsSubclass (widget, commandWidgetClass)) { Dimension bw = 0; @@ -154,6 +183,14 @@ XtRemoveAllCallbacks (widget, XtNcallback); XtAddCallback (widget, XtNcallback, xaw_generic_callback, instance); +#ifdef LWLIB_WIDGETS_ATHENA + /* set the selected state */ + if (XtIsSubclass (widget, toggleWidgetClass)) + { + XtSetArg (al [0], XtNstate, val->selected); + XtSetValues (widget, al, 1); + } +#endif /* LWLIB_WIDGETS_ATHENA */ } #endif /* LWLIB_DIALOGS_ATHENA */ } @@ -162,9 +199,36 @@ xaw_update_one_value (widget_instance *instance, Widget widget, widget_value *val) { - /* This function is not used by the scrollbars and those are the only - Athena widget implemented at the moment so do nothing. */ - return; +#ifdef LWLIB_WIDGETS_ATHENA + widget_value *old_wv; + + /* copy the call_data slot into the "return" widget_value */ + for (old_wv = instance->info->val->contents; old_wv; old_wv = old_wv->next) + if (!strcmp (val->name, old_wv->name)) + { + val->call_data = old_wv->call_data; + break; + } + + if (XtIsSubclass (widget, toggleWidgetClass)) + { + Arg al [1]; + XtSetArg (al [0], XtNstate, &val->selected); + XtGetValues (widget, al, 1); + val->edited = True; + } +#ifndef NEED_MOTIF + else if (XtIsSubclass (widget, asciiTextWidgetClass)) + { + Arg al [1]; + if (val->value) + free (val->value); + XtSetArg (al [0], XtNstring, &val->value); + XtGetValues (widget, al, 1); + val->edited = True; + } +#endif +#endif /* LWLIB_WIDGETS_ATHENA */ } void @@ -440,7 +504,21 @@ Widget instance_widget; LWLIB_ID id; XtPointer user_data; +#ifdef LWLIB_WIDGETS_ATHENA + /* We want the selected status to change only when we decide it + should change. Yuck but correct. */ + if (XtIsSubclass (widget, toggleWidgetClass)) + { + Boolean check; + Arg al [1]; + XtSetArg (al [0], XtNstate, &check); + XtGetValues (widget, al, 1); + + XtSetArg (al [0], XtNstate, !check); + XtSetValues (widget, al, 1); + } +#endif /* LWLIB_WIDGETS_ATHENA */ lw_internal_update_other_instances (widget, closure, call_data); if (! instance) @@ -464,17 +542,26 @@ #else /* Damn! Athena doesn't give us a way to hang our own data on the buttons, so we have to go find it... I guess this assumes that - all instances of a button have the same call data. */ + all instances of a button have the same call data. + + ... Which is a totally bogus assumption --andyp */ { - widget_value *val = instance->info->val->contents; - char *name = XtName (widget); - while (val) + widget_value *val = instance->info->val; + /* If the widget is a buffer/gutter widget then we already have + the one we are looking for, so don't try and descend the widget + tree. */ + if (val->contents) { - if (val->name && !strcmp (val->name, name)) - break; - val = val->next; + char *name = XtName (widget); + val = val->contents; + while (val) + { + if (val->name && !strcmp (val->name, name)) + break; + val = val->next; + } + if (! val) abort (); } - if (! val) abort (); user_data = val->call_data; } #endif @@ -614,12 +701,163 @@ } #endif /* LWLIB_SCROLLBARS_ATHENA */ +#ifdef LWLIB_WIDGETS_ATHENA +/* glyph widgets */ +static Widget +xaw_create_button (widget_instance *instance) +{ + Arg al[20]; + int ac = 0; + Widget button = 0; + widget_value* val = instance->info->val; + + XtSetArg (al [ac], XtNsensitive, val->enabled); ac++; + XtSetArg (al [ac], XtNmappedWhenManaged, FALSE); ac++; + XtSetArg (al [ac], XtNjustify, XtJustifyCenter); ac++; + /* The highlight doesn't appear to be dynamically set which makes it + look ugly. I think this may be a LessTif bug but for now we just + get rid of it. */ + XtSetArg (al [ac], XtNhighlightThickness, (Dimension)0);ac++; + + /* add any args the user supplied for creation time */ + lw_add_value_args_to_args (val, al, &ac); + + if (!val->call_data) + button = XtCreateManagedWidget (val->name, labelWidgetClass, + instance->parent, al, ac); + + else + { + if (val->type == TOGGLE_TYPE || val->type == RADIO_TYPE) + { + XtSetArg (al [ac], XtNstate, val->selected); ac++; + button = XtCreateManagedWidget + (val->name, + val->type == TOGGLE_TYPE ? checkboxWidgetClass : radioWidgetClass, + instance->parent, al, ac); + } + else + { + button = XtCreateManagedWidget (val->name, commandWidgetClass, + instance->parent, al, ac); + } + XtRemoveAllCallbacks (button, XtNcallback); + XtAddCallback (button, XtNcallback, xaw_generic_callback, (XtPointer)instance); + } + + XtManageChild (button); + + return button; +} + +static Widget +xaw_create_label_field (widget_instance *instance) +{ + return xaw_create_label (instance->parent, instance->info->val); +} + +Widget +xaw_create_label (Widget parent, widget_value* val) +{ + Arg al[20]; + int ac = 0; + Widget label = 0; + + XtSetArg (al [ac], XtNsensitive, val->enabled); ac++; + XtSetArg (al [ac], XtNmappedWhenManaged, FALSE); ac++; + XtSetArg (al [ac], XtNjustify, XtJustifyCenter); ac++; + + /* add any args the user supplied for creation time */ + lw_add_value_args_to_args (val, al, &ac); + + label = XtCreateManagedWidget (val->name, labelWidgetClass, + parent, al, ac); + + /* Do it again for arguments that have no effect until the widget is realized. */ + ac = 0; + lw_add_value_args_to_args (val, al, &ac); + XtSetValues (label, al, ac); + + return label; +} + +static Widget +xaw_create_progress (widget_instance *instance) +{ + Arg al[20]; + int ac = 0; + Widget scale = 0; + widget_value* val = instance->info->val; + + if (!val->call_data) + { + XtSetArg (al [ac], XtNsensitive, False); ac++; + } + else + { + XtSetArg (al [ac], XtNsensitive, val->enabled); ac++; + } + XtSetArg (al [ac], XtNmappedWhenManaged, FALSE); ac++; + XtSetArg (al [ac], XtNorientation, XtorientHorizontal); ac++; + XtSetArg (al [ac], XtNhighlightThickness, (Dimension)0);ac++; + XtSetArg (al [ac], XtNntics, (Cardinal)10);ac++; + + /* add any args the user supplied for creation time */ + lw_add_value_args_to_args (val, al, &ac); + + scale = XtCreateManagedWidget (val->name, gaugeWidgetClass, + instance->parent, al, ac); + /* add the callback */ + if (val->call_data) + XtAddCallback (scale, XtNgetValue, xaw_generic_callback, (XtPointer)instance); + + XtManageChild (scale); + + return scale; +} + +#ifndef NEED_MOTIF +static Widget +xaw_create_text_field (widget_instance *instance) +{ + Arg al[20]; + int ac = 0; + Widget text = 0; + widget_value* val = instance->info->val; + + XtSetArg (al [ac], XtNsensitive, val->enabled && val->call_data); ac++; + XtSetArg (al [ac], XtNmappedWhenManaged, FALSE); ac++; + XtSetArg (al [ac], XtNhighlightThickness, (Dimension)0); ac++; + XtSetArg (al [ac], XtNtype, XawAsciiString); ac++; + XtSetArg (al [ac], XtNeditType, XawtextEdit); ac++; + + /* add any args the user supplied for creation time */ + lw_add_value_args_to_args (val, al, &ac); + + text = XtCreateManagedWidget (val->name, asciiTextWidgetClass, + instance->parent, al, ac); + XtManageChild (text); + + return text; +} +#endif +#endif /* LWLIB_WIDGETS_ATHENA */ + widget_creation_entry xaw_creation_table [] = { #ifdef LWLIB_SCROLLBARS_ATHENA - {"vertical-scrollbar", xaw_create_vertical_scrollbar}, - {"horizontal-scrollbar", xaw_create_horizontal_scrollbar}, + {"vertical-scrollbar", xaw_create_vertical_scrollbar }, + {"horizontal-scrollbar", xaw_create_horizontal_scrollbar }, +#endif +#ifdef LWLIB_WIDGETS_ATHENA + {"button", xaw_create_button }, + { "label", xaw_create_label_field }, +#ifndef NEED_MOTIF + {"text-field", xaw_create_text_field }, +#endif + {"progress", xaw_create_progress }, #endif {NULL, NULL} }; + diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib-Xaw.h --- a/lwlib/lwlib-Xaw.h Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib-Xaw.h Mon Aug 13 11:26:11 2007 +0200 @@ -8,6 +8,9 @@ Widget xaw_create_dialog (widget_instance* instance); +Widget +xaw_create_label (Widget parent, widget_value* val); + Boolean lw_xaw_widget_p (Widget widget); diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib-Xlw.c --- a/lwlib/lwlib-Xlw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib-Xlw.c Mon Aug 13 11:26:11 2007 +0200 @@ -20,20 +20,35 @@ #include #include /* for abort () */ +#include /* for abort () */ #include #include "lwlib-Xlw.h" +#include "lwlib-utils.h" #include #include #include #include #include +#ifdef HAVE_WIDGETS +#include "../src/EmacsManager.h" +#endif #ifdef LWLIB_MENUBARS_LUCID #include "xlwmenu.h" #endif #ifdef LWLIB_SCROLLBARS_LUCID #include "xlwscrollbar.h" #endif +#ifdef LWLIB_TABS_LUCID +#ifdef NEED_MOTIF +#include "lwlib-Xm.h" +#endif +#ifdef NEED_ATHENA +#include "lwlib-Xaw.h" +#endif +#include "../src/xmu.h" +#include "xlwtabs.h" +#endif @@ -301,6 +316,172 @@ #endif /* LWLIB_SCROLLBARS_LUCID */ +#ifdef LWLIB_TABS_LUCID +/* tab control + + lwlib is such an incredible hairy crock. I just cannot believe + it! There are random dependencies between functions, there is a + total lack of genericity, even though it initially appears to be + generic. It should all be junked and begun again. Building tabs are + an example - in theory we should be able to reuse a lot of the + general stuff because we want to put labels of whatever toolkit we + are using in the tab. Instead we have to hack it by hand. */ +static void +xlw_tab_control_callback (Widget w, XtPointer client_data, XtPointer call_data) +{ + /* call data is the topmost widget */ + widget_instance* instance = (widget_instance*)client_data; + Widget top = (Widget)call_data; + char *name = XtName (top); + widget_value* widget_val; + XtPointer widget_arg; + LWLIB_ID id; + lw_callback post_activate_cb; + + if (w->core.being_destroyed) + return; + + /* Grab these values before running any functions, in case running + the selection_cb causes the widget to be destroyed. */ + id = instance->info->id; + post_activate_cb = instance->info->post_activate_cb; + + /* search for the widget_val for the selected tab */ + for (widget_val = instance->info->val->contents; widget_val; + widget_val = widget_val->next) + { + if (!strcmp (widget_val->name, name)) + break; + } + + widget_arg = widget_val ? widget_val->call_data : NULL; + + if (instance->info->selection_cb && + widget_val && + widget_val->enabled && + !widget_val->contents) + instance->info->selection_cb (w, id, widget_arg); + + if (post_activate_cb) + post_activate_cb (w, id, widget_arg); +} + +static Widget +xlw_create_tab_control (widget_instance *instance) +{ + Arg al[20]; + int ac = 0; + Widget tab = 0; + widget_value* val = instance->info->val; + + XtSetArg (al [ac], XtNsensitive, val->enabled); ac++; + XtSetArg (al [ac], XtNmappedWhenManaged, FALSE); ac++; + XtSetArg (al [ac], XtNorientation, XtorientHorizontal); ac++; + XtSetArg (al [ac], XtNresizable, False); ac++; + + /* add any args the user supplied for creation time */ + lw_add_value_args_to_args (val, al, &ac); + + tab = XtCreateManagedWidget (val->name, tabsWidgetClass, + instance->parent, al, ac); + XtRemoveAllCallbacks (tab, XtNcallback); + XtAddCallback (tab, XtNcallback, xlw_tab_control_callback, (XtPointer)instance); + + XtManageChild (tab); + + return tab; +} + +static void build_tabs_in_widget (widget_instance* instance, Widget widget, + widget_value* val) +{ + widget_value* cur = val; + for (cur = val; cur; cur = cur->next) + { + if (cur->value) + { +#ifdef LWLIB_WIDGETS_MOTIF + xm_create_label (widget, cur); +#else + xaw_create_label (widget, cur); +#endif + } + cur->change = NO_CHANGE; + } +} + +static void +xlw_update_tab_control (widget_instance* instance, Widget widget, widget_value* val) +{ + Widget* children; + unsigned int num_children; + int i; + widget_value *cur = 0; + + XtRemoveAllCallbacks (widget, XtNcallback); + XtAddCallback (widget, XtNcallback, xlw_tab_control_callback, (XtPointer)instance); + + if (val->change == STRUCTURAL_CHANGE + || + (val->contents && val->contents->change == STRUCTURAL_CHANGE)) + { + destroy_all_children (widget); + build_tabs_in_widget (instance, widget, val->contents); + } + + children = XtCompositeChildren (widget, &num_children); + if (children) + { + for (i = 0, cur = val->contents; i < num_children; i++) + { + if (!cur) + abort (); + if (children [i]->core.being_destroyed + || strcmp (XtName (children [i]), cur->name)) + continue; +#ifdef NEED_MOTIF + if (lw_motif_widget_p (children [i])) + xm_update_one_widget (instance, children [i], cur, False); +#endif +#ifdef NEED_ATHENA + if (lw_xaw_widget_p (children [i])) + xaw_update_one_widget (instance, children [i], cur, False); +#endif + cur = cur->next; + } + XtFree ((char *) children); + } + if (cur) + abort (); +} +#endif /* LWLIB_TABS_LUCID */ + +#ifdef HAVE_WIDGETS +static Widget +xlw_create_clip_window (widget_instance *instance) +{ + Arg al[20]; + int ac = 0; + Widget clip = 0; + widget_value* val = instance->info->val; + + XtSetArg (al [ac], XtNmappedWhenManaged, FALSE); ac++; + XtSetArg (al [ac], XtNsensitive, TRUE); ac++; + /* add any args the user supplied for creation time */ + lw_add_value_args_to_args (val, al, &ac); + + /* Create a clip window to contain the subwidget. Incredibly the + XEmacs manager seems to be the most appropriate widget for + this. Nothing else is simple enough and yet does what is + required. */ + clip = XtCreateManagedWidget (val->name, + emacsManagerWidgetClass, + instance->parent, al, ac); + + return clip; +} +#endif + widget_creation_entry xlw_creation_table [] = { @@ -312,6 +493,12 @@ {"vertical-scrollbar", xlw_create_vertical_scrollbar}, {"horizontal-scrollbar", xlw_create_horizontal_scrollbar}, #endif +#ifdef LWLIB_TABS_LUCID + {"tab-control", xlw_create_tab_control}, +#endif +#ifdef HAVE_WIDGETS + {"clip-window", xlw_create_clip_window}, +#endif {NULL, NULL} }; @@ -327,6 +514,10 @@ if (the_class == xlwScrollBarWidgetClass) return True; #endif +#ifdef LWLIB_TABS_LUCID + if (the_class == tabsWidgetClass) + return True; +#endif #ifdef LWLIB_MENUBARS_LUCID if (the_class == overrideShellWidgetClass) return @@ -340,9 +531,7 @@ xlw_update_one_widget (widget_instance* instance, Widget widget, widget_value* val, Boolean deep_p) { - WidgetClass class; - - class = XtClass (widget); + WidgetClass class = XtClass (widget); if (0) ; @@ -365,6 +554,12 @@ xlw_update_scrollbar (instance, widget, val); } #endif +#ifdef LWLIB_TABS_LUCID + else if (class == tabsWidgetClass) + { + xlw_update_tab_control (instance, widget, val); + } +#endif } void diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib-Xm.c --- a/lwlib/lwlib-Xm.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib-Xm.c Mon Aug 13 11:26:11 2007 +0200 @@ -60,9 +60,11 @@ #include #include #include +#ifdef LWLIB_WIDGETS_MOTIF #include #if XmVERSION > 1 -#include +#include +#endif #endif #ifdef LWLIB_MENUBARS_MOTIF @@ -72,7 +74,9 @@ XtPointer); static void xm_pop_down_callback (Widget, XtPointer, XtPointer); static void xm_generic_callback (Widget, XtPointer, XtPointer); -#ifdef LWLIB_DIALOGS_MOTIF +static void mark_dead_instance_destroyed (Widget widget, XtPointer closure, + XtPointer call_data); +#if defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_WIDGETS_MOTIF) static void xm_nosel_callback (Widget, XtPointer, XtPointer); #endif #ifdef LWLIB_SCROLLBARS_MOTIF @@ -171,35 +175,6 @@ return result; } -#ifdef LWLIB_MENUBARS_MOTIF - -static void -destroy_all_children (Widget widget) -{ - Widget* children; - unsigned int number; - int i; - - children = XtCompositeChildren (widget, &number); - if (children) - { - /* Unmanage all children and destroy them. They will only be - * really destroyed when we get out of DispatchEvent. */ - for (i = 0; i < number; i++) - { - Widget child = children [i]; - if (!child->core.being_destroyed) - { - XtUnmanageChild (child); - XtDestroyWidget (child); - } - } - XtFree ((char *) children); - } -} - -#endif /* LWLIB_MENUBARS_MOTIF */ - #ifdef LWLIB_DIALOGS_MOTIF @@ -221,7 +196,7 @@ #endif /* LWLIB_DIALOGS_MOTIF */ -#if defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_MENUBARS_MOTIF) +#if defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_MENUBARS_MOTIF) || defined (LWLIB_WIDGETS_MOTIF) /* update the label of anything subclass of a label */ static void @@ -233,6 +208,14 @@ XmString name_string = NULL; Arg al [20]; int ac = 0; + int type; + + /* Don't clobber pixmap types. */ + XtSetArg (al [0], XmNlabelType, &type); + XtGetValues (widget, al, 1); + + if (type == XmPIXMAP) + return; if (val->value) { @@ -262,24 +245,30 @@ char *res_name = NULL; res_name = resource_string (widget, val->name); + /* Concatenating the value with itself seems just plain daft. */ if (!res_name) - res_name = val->name; - - name_string = - XmStringCreateLtoR (res_name, XmSTRING_DEFAULT_CHARSET); - - value_name = XtMalloc (strlen (val->value) + 2); - *value_name = 0; - strcat (value_name, " "); - strcat (value_name, val->value); - - val_string = - XmStringCreateLtoR (value_name, XmSTRING_DEFAULT_CHARSET); - - built_string = - XmStringConcat (name_string, val_string); - - XtFree (value_name); + { + built_string = + XmStringCreateLtoR (val->value, XmSTRING_DEFAULT_CHARSET); + } + else + { + name_string = + XmStringCreateLtoR (res_name, XmSTRING_DEFAULT_CHARSET); + + value_name = XtMalloc (strlen (val->value) + 2); + *value_name = 0; + strcat (value_name, " "); + strcat (value_name, val->value); + + val_string = + XmStringCreateLtoR (value_name, XmSTRING_DEFAULT_CHARSET); + + built_string = + XmStringConcat (name_string, val_string); + + XtFree (value_name); + } } XtSetArg (al [ac], XmNlabelString, built_string); ac++; @@ -303,6 +292,9 @@ if (name_string) XmStringFree (name_string); + + if (val_string) + XmStringFree (val_string); } #endif /* defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_MENUBARS_MOTIF) */ @@ -380,7 +372,7 @@ instance); XtSetArg (al [0], XmNset, val->selected); XtSetArg (al [1], XmNalignment, XmALIGNMENT_BEGINNING); - XtSetValues (widget, al, 2); + XtSetValues (widget, al, 1); } static void @@ -425,6 +417,29 @@ } } +#if defined (LWLIB_WIDGETS_MOTIF) && XmVERSION > 1 +/* update of combo box */ +static void +xm_update_combo_box (widget_instance* instance, Widget widget, widget_value* val) +{ + widget_value* cur; + int i; + XtRemoveAllCallbacks (widget, XmNselectionCallback); + XtAddCallback (widget, XmNselectionCallback, xm_generic_callback, + instance); + for (cur = val->contents, i = 0; cur; cur = cur->next) + if (cur->value) + { + XmString xmstr = XmStringCreate (cur->value, XmSTRING_DEFAULT_CHARSET); + i += 1; + XmListAddItem (CB_List (widget), xmstr, 0); + if (cur->selected) + XmListSelectPos (CB_List (widget), i, False); + XmStringFree (xmstr); + } +} +#endif + #ifdef LWLIB_MENUBARS_MOTIF /* update a popup menu, pulldown menu or a menubar */ @@ -767,22 +782,24 @@ widget_value* val, Boolean deep_p) { WidgetClass class; - Arg al [2]; + Arg al [20]; + int ac = 0; /* Mark as not edited */ val->edited = False; /* Common to all widget types */ - XtSetArg (al [0], XmNsensitive, val->enabled); - XtSetArg (al [1], XmNuserData, val->call_data); - XtSetValues (widget, al, 2); + XtSetArg (al [ac], XmNsensitive, val->enabled); ac++; + XtSetArg (al [ac], XmNuserData, val->call_data); ac++; + lw_add_value_args_to_args (val, al, &ac); -#if defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_MENUBARS_MOTIF) + XtSetValues (widget, al, ac); + +#if defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_MENUBARS_MOTIF) || defined (LWLIB_WIDGETS_MOTIF) /* Common to all label like widgets */ if (XtIsSubclass (widget, xmLabelWidgetClass)) xm_update_label (instance, widget, val); -#endif /* defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_MENUBARS_MOTIF) */ - +#endif class = XtClass (widget); /* Class specific things */ if (class == xmPushButtonWidgetClass || @@ -827,6 +844,12 @@ { xm_update_list (instance, widget, val); } +#if defined (LWLIB_WIDGETS_MOTIF) && XmVERSION > 1 + else if (class == xmComboBoxWidgetClass) + { + xm_update_combo_box (instance, widget, val); + } +#endif #ifdef LWLIB_SCROLLBARS_MOTIF else if (class == xmScrollBarWidgetClass) { @@ -903,11 +926,20 @@ val->edited = True; } } - else if (class == xmListWidgetClass) + else if (class == xmListWidgetClass +#if defined (LWLIB_WIDGETS_MOTIF) && XmVERSION > 1 + || class == xmComboBoxWidgetClass +#endif + ) { int pos_cnt; int* pos_list; - if (XmListGetSelectedPos (widget, &pos_list, &pos_cnt)) + Widget list = widget; +#if defined (LWLIB_WIDGETS_MOTIF) && XmVERSION > 1 + if (class == xmComboBoxWidgetClass) + list = CB_List (widget); +#endif + if (XmListGetSelectedPos (list, &pos_list, &pos_cnt)) { int i; widget_value* cur; @@ -1316,14 +1348,6 @@ } static void -mark_dead_instance_destroyed (Widget widget, XtPointer closure, - XtPointer call_data) -{ - destroyed_instance* instance = (destroyed_instance*)closure; - instance->widget = NULL; -} - -static void recenter_widget (Widget widget) { Widget parent = XtParent (widget); @@ -1566,9 +1590,10 @@ #endif /* LWLIB_SCROLLBARS_MOTIF */ +#ifdef LWLIB_WIDGETS_MOTIF /* glyph widgets */ static Widget -make_button (widget_instance *instance) +xm_create_button (widget_instance *instance) { Arg al[20]; int ac = 0; @@ -1615,14 +1640,21 @@ } static Widget -make_progress (widget_instance *instance) +xm_create_progress (widget_instance *instance) { Arg al[20]; int ac = 0; Widget scale = 0; widget_value* val = instance->info->val; - XtSetArg (al [ac], XmNsensitive, val->enabled); ac++; + if (!val->call_data) + { + XtSetArg (al [ac], XmNsensitive, False); ac++; + } + else + { + XtSetArg (al [ac], XmNsensitive, val->enabled); ac++; + } XtSetArg (al [ac], XmNalignment, XmALIGNMENT_BEGINNING); ac++; XtSetArg (al [ac], XmNuserData, val->call_data); ac++; XtSetArg (al [ac], XmNmappedWhenManaged, FALSE); ac++; @@ -1631,9 +1663,6 @@ look ugly. I think this may be a LessTif bug but for now we just get rid of it. */ XtSetArg (al [ac], XmNhighlightThickness, (Dimension)0);ac++; - if (!val->call_data) - XtSetArg (al [ac], XmNsensitive, False); ac++; - /* add any args the user supplied for creation time */ lw_add_value_args_to_args (val, al, &ac); @@ -1648,7 +1677,7 @@ } static Widget -make_text_field (widget_instance *instance) +xm_create_text_field (widget_instance *instance) { Arg al[20]; int ac = 0; @@ -1677,9 +1706,45 @@ return text; } +static Widget +xm_create_label_field (widget_instance *instance) +{ + return xm_create_label (instance->parent, instance->info->val); +} + +Widget +xm_create_label (Widget parent, widget_value* val) +{ + Arg al[20]; + int ac = 0; + Widget label = 0; + + XtSetArg (al [ac], XmNsensitive, val->enabled); ac++; + XtSetArg (al [ac], XmNalignment, XmALIGNMENT_BEGINNING); ac++; + XtSetArg (al [ac], XmNmappedWhenManaged, FALSE); ac++; + /* The highlight doesn't appear to be dynamically set which makes it + look ugly. I think this may be a LessTif bug but for now we just + get rid of it. */ + XtSetArg (al [ac], XmNhighlightThickness, (Dimension)0);ac++; + + /* add any args the user supplied for creation time */ + lw_add_value_args_to_args (val, al, &ac); + + label = XmCreateLabel (parent, val->name, al, ac); + + XtManageChild (label); + + /* Do it again for arguments that have no effect until the widget is realized. */ + ac = 0; + lw_add_value_args_to_args (val, al, &ac); + XtSetValues (label, al, ac); + + return label; +} + #if XmVERSION > 1 static Widget -make_combo_box (widget_instance *instance) +xm_create_combo_box (widget_instance *instance) { Arg al[20]; int ac = 0; @@ -1698,7 +1763,7 @@ /* add any args the user supplied for creation time */ lw_add_value_args_to_args (val, al, &ac); - combo = XmCreateComboBox (instance->parent, val->name, al, ac); + combo = XmCreateDropDownComboBox (instance->parent, val->name, al, ac); if (val->call_data) XtAddCallback (combo, XmNselectionCallback, xm_generic_callback, (XtPointer)instance); @@ -1708,6 +1773,7 @@ return combo; } #endif +#endif /* LWLIB_WIDGETS_MOTIF */ /* Table of functions to create widgets */ @@ -1723,11 +1789,14 @@ {"vertical-scrollbar", make_vertical_scrollbar}, {"horizontal-scrollbar", make_horizontal_scrollbar}, #endif - {"button", make_button}, - {"progress", make_progress}, - {"text-field", make_text_field}, +#ifdef LWLIB_WIDGETS_MOTIF + {"button", xm_create_button}, + {"progress", xm_create_progress}, + {"text-field", xm_create_text_field}, + {"label", xm_create_label_field}, #if XmVERSION > 1 - {"combo-box", make_combo_box}, + {"combo-box", xm_create_combo_box}, +#endif #endif {NULL, NULL} }; @@ -1736,7 +1805,7 @@ void xm_destroy_instance (widget_instance* instance) { -#ifdef LWLIB_DIALOGS_MOTIF +#if defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_WIDGETS_MOTIF) /* It appears that this is used only for dialog boxes. */ Widget widget = instance->widget; /* recycle the dialog boxes */ @@ -1767,7 +1836,7 @@ XtDestroyWidget (instance->widget); } -#endif /* LWLIB_DIALOGS_MOTIF */ +#endif /* LWLIB_DIALOGS_MOTIF || LWLIB_WIDGETS_MOTIF */ } /* popup utility */ @@ -1920,7 +1989,7 @@ static void xm_generic_callback (Widget widget, XtPointer closure, XtPointer call_data) { -#if (defined (LWLIB_MENUBARS_MOTIF) || defined (LWLIB_DIALOGS_MOTIF)) +#if (defined (LWLIB_MENUBARS_MOTIF) || defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_WIDGETS_MOTIF)) /* We want the selected status to change only when we decide it should change. Yuck but correct. */ if (XtClass (widget) == xmToggleButtonWidgetClass @@ -1946,25 +2015,6 @@ do_call (widget, closure, post_activate); } -#ifdef LWLIB_DIALOGS_MOTIF - -static void -xm_nosel_callback (Widget widget, XtPointer closure, XtPointer call_data) -{ - /* This callback is only called when a dialog box is dismissed with the wm's - destroy button (WM_DELETE_WINDOW.) We want the dialog box to be destroyed - in that case, not just unmapped, so that it releases its keyboard grabs. - But there are problems with running our callbacks while the widget is in - the process of being destroyed, so we set XmNdeleteResponse to XmUNMAP - instead of XmDESTROY and then destroy it ourself after having run the - callback. - */ - do_call (widget, closure, no_selection); - XtDestroyWidget (widget); -} - -#endif - #ifdef LWLIB_MENUBARS_MOTIF static void @@ -2073,6 +2123,31 @@ } #endif /* LWLIB_SCROLLBARS_MOTIF */ +#if defined (LWLIB_DIALOGS_MOTIF) || defined (LWLIB_WIDGETS_MOTIF) +static void +mark_dead_instance_destroyed (Widget widget, XtPointer closure, + XtPointer call_data) +{ + destroyed_instance* instance = (destroyed_instance*)closure; + instance->widget = NULL; +} + +static void +xm_nosel_callback (Widget widget, XtPointer closure, XtPointer call_data) +{ + /* This callback is only called when a dialog box is dismissed with the wm's + destroy button (WM_DELETE_WINDOW.) We want the dialog box to be destroyed + in that case, not just unmapped, so that it releases its keyboard grabs. + But there are problems with running our callbacks while the widget is in + the process of being destroyed, so we set XmNdeleteResponse to XmUNMAP + instead of XmDESTROY and then destroy it ourself after having run the + callback. + */ + do_call (widget, closure, no_selection); + XtDestroyWidget (widget); +} +#endif + /* set the keyboard focus */ void diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib-Xm.h --- a/lwlib/lwlib-Xm.h Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib-Xm.h Mon Aug 13 11:26:11 2007 +0200 @@ -8,6 +8,9 @@ Widget xm_create_dialog (widget_instance* instance); +Widget +xm_create_label (Widget parent, widget_value* val); + Boolean lw_motif_widget_p (Widget widget); diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib-config.c --- a/lwlib/lwlib-config.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib-config.c Mon Aug 13 11:26:11 2007 +0200 @@ -88,3 +88,13 @@ int lwlib_does_not_support_dialogs; # endif #endif + +#ifdef LWLIB_WIDGETS_MOTIF +int lwlib_widgets_motif; +#else +# ifdef LWLIB_WIDGETS_ATHENA +int lwlib_widgets_athena; +# else +int lwlib_does_not_support_widgets; +# endif +#endif diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib-utils.c --- a/lwlib/lwlib-utils.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib-utils.c Mon Aug 13 11:26:11 2007 +0200 @@ -31,6 +31,31 @@ #include #include "lwlib-utils.h" +void +destroy_all_children (Widget widget) +{ + Widget* children; + unsigned int number; + int i; + + children = XtCompositeChildren (widget, &number); + if (children) + { + /* Unmanage all children and destroy them. They will only be + * really destroyed when we get out of DispatchEvent. */ + for (i = 0; i < number; i++) + { + Widget child = children [i]; + if (!child->core.being_destroyed) + { + XtUnmanageChild (child); + XtDestroyWidget (child); + } + } + XtFree ((char *) children); + } +} + /* Redisplay the contents of the widget, without first clearing it. */ void XtNoClearRefreshWidget (Widget widget) diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib-utils.h --- a/lwlib/lwlib-utils.h Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib-utils.h Mon Aug 13 11:26:11 2007 +0200 @@ -1,6 +1,7 @@ #ifndef _LWLIB_UTILS_H_ #define _LWLIB_UTILS_H_ +void destroy_all_children (Widget widget); void XtNoClearRefreshWidget (Widget); typedef void (*XtApplyToWidgetsProc) (Widget, XtPointer); diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib.c --- a/lwlib/lwlib.c Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib.c Mon Aug 13 11:26:11 2007 +0200 @@ -125,8 +125,6 @@ widget_value_free_list = wv; } -static void free_widget_value_tree (widget_value *wv); - static void free_widget_value_contents (widget_value *wv) { @@ -155,11 +153,13 @@ free_widget_value_tree (wv->contents); wv->contents = (widget_value *) 0xDEADBEEF; } - if (wv->args && wv->free_args) + if (wv->args && wv->nargs) { - free (wv->args); - wv->args = (void *) 0xDEADBEEF; + if (wv->free_args) + free (wv->args); + wv->args = (ArgList) 0xDEADBEEF; wv->nargs = 0; + wv->free_args = 0; } if (wv->next) { @@ -168,7 +168,7 @@ } } -static void +void free_widget_value_tree (widget_value *wv) { if (!wv) @@ -1326,3 +1326,4 @@ *offset += wv->nargs; } } + diff -r 28d9c139be4c -r 11054d720c21 lwlib/lwlib.h --- a/lwlib/lwlib.h Mon Aug 13 11:25:03 2007 +0200 +++ b/lwlib/lwlib.h Mon Aug 13 11:26:11 2007 +0200 @@ -181,6 +181,10 @@ /* do this for the other toolkits too */ #endif /* LWLIB_MENUBARS_LUCID */ +#if defined (LWLIB_TABS_LUCID) +#include "xlwtabs.h" +#endif + void lw_register_widget (CONST char* type, CONST char* name, LWLIB_ID id, widget_value* val, lw_callback pre_activate_cb, lw_callback selection_cb, @@ -210,6 +214,7 @@ widget_value *malloc_widget_value (void); void free_widget_value (widget_value *); +void free_widget_value_tree (widget_value *wv); widget_value *replace_widget_value_tree (widget_value*, widget_value*); void lw_popup_menu (Widget, XEvent *); diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwcheckbox.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwcheckbox.c Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,415 @@ +/* Checkbox Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* Synched up with: Checkbox.c 1.1 */ + +/* + * Checkbox.c - Checkbox button widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: June 30, 1997 + * + * Overview: This widget is identical to the Radio widget in behavior, + * except that the button is square and has a check mark. + */ + + +#include +#include + +#include +#include +#include +#include "../src/xmu.h" +#include "xlwcheckboxP.h" + + +/* by using the same size for the checkbox as for the diamond box, + * we can let the Radio widget do the vast majority of the work. + */ + +#define BOX_SIZE 8 +#define DRAW_CHECK 0 /* don't draw the check mark */ + +#define cclass(w) ((CheckboxWidgetClass)((w)->core.widget_class)) + +#ifdef _ThreeDP_h +#define swid(cw) ((cw)->threeD.shadow_width) +#else +#define swid(cw) ((cw)->core.border_width) +#endif + +#define bsize(cw) (cclass(cw)->radio_class.dsize) +#define bs(cw) (bsize(cw) + 2*swid(cw)) + + +#if DRAW_CHECK +#define check_width 14 +#define check_height 14 +static u_char check_bits[] = { + 0x00, 0x00, 0x00, 0x20, 0x00, 0x18, 0x00, 0x0c, 0x00, 0x06, 0x00, 0x03, + 0x8c, 0x03, 0xde, 0x01, 0xff, 0x01, 0xfe, 0x00, 0xfc, 0x00, 0x78, 0x00, + 0x70, 0x00, 0x20, 0x00}; +#endif + + +/**************************************************************** + * + * Full class record constant + * + ****************************************************************/ + + +#if DRAW_CHECK +static char defaultTranslations[] = + ": highlight()\n\ + : unpress(draw) unhighlight()\n\ + : press()\n\ + ,: unpress(nodraw) toggle() notify()"; +#endif + + + +#define offset(field) XtOffsetOf(CheckboxRec, field) +static XtResource resources[] = { + {XtNtristate, XtCTristate, XtRBoolean, sizeof(Boolean), + offset(checkbox.tristate), XtRImmediate, (XtPointer)FALSE}, +} ; +#undef offset + + /* Member functions */ + +static void CheckboxClassInit (void); +static void CheckboxInit (Widget, Widget, ArgList, Cardinal *); +#if DRAW_CHECK +static void CheckboxRealize (Widget, Mask *, XSetWindowAttributes *); +#endif +static void DrawCheck (Widget); + + + /* Action procs */ +#if DRAW_CHECK +static void CheckboxPress (Widget, XEvent *, String *, Cardinal *); +static void CheckboxUnpress (Widget, XEvent *, String *, Cardinal *); +#endif + + /* internal privates */ + +#if DRAW_CHECK +static XtActionsRec actionsList[] = +{ + {"press", CheckboxPress}, + {"unpress", CheckboxUnpress}, +} ; +#endif + +#define SuperClass ((RadioWidgetClass)&radioClassRec) + +CheckboxClassRec checkboxClassRec = { + { + (WidgetClass) SuperClass, /* superclass */ + "Checkbox", /* class_name */ + sizeof(CheckboxRec), /* size */ + CheckboxClassInit, /* class_initialize */ + NULL, /* class_part_initialize */ + FALSE, /* class_inited */ + CheckboxInit, /* initialize */ + NULL, /* initialize_hook */ +#if DRAW_CHECK + CheckboxRealize, /* realize */ + actionsList, /* actions */ + XtNumber(actionsList), /* num_actions */ +#else + XtInheritRealize, /* realize */ + NULL, /* actions */ + 0, /* num_actions */ +#endif + resources, /* resources */ + XtNumber(resources), /* resource_count */ + NULLQUARK, /* xrm_class */ + TRUE, /* compress_motion */ + TRUE, /* compress_exposure */ + TRUE, /* compress_enterleave */ + FALSE, /* visible_interest */ + NULL, /* destroy */ + XtInheritResize, /* resize */ + XtInheritExpose, /* expose */ + NULL, /* set_values */ + NULL, /* set_values_hook */ + XtInheritSetValuesAlmost, /* set_values_almost */ + NULL, /* get_values_hook */ + NULL, /* accept_focus */ + XtVersion, /* version */ + NULL, /* callback_private */ +#if DRAW_CHECK + defaultTranslations, /* tm_table */ +#else + XtInheritTranslations, /* tm_table */ +#endif + XtInheritQueryGeometry, /* query_geometry */ + XtInheritDisplayAccelerator, /* display_accelerator */ + NULL /* extension */ + }, /* CoreClass fields initialization */ + { + XtInheritChangeSensitive /* change_sensitive */ + }, /* SimpleClass fields initialization */ +#ifdef _ThreeDP_h + { + XtInheritXaw3dShadowDraw /* field not used */ + }, /* ThreeDClass fields initialization */ +#endif + { + 0 /* field not used */ + }, /* LabelClass fields initialization */ + { + 0 /* field not used */ + }, /* CommandClass fields initialization */ + { + RadioSet, /* Set Procedure. */ + RadioUnset, /* Unset Procedure. */ + NULL /* extension. */ + }, /* ToggleClass fields initialization */ + { + BOX_SIZE, + DrawCheck, /* draw procedure */ + NULL /* extension. */ + }, /* RadioClass fields initialization */ + { + NULL /* extension. */ + }, /* CheckboxClass fields initialization */ +}; + + /* for public consumption */ +WidgetClass checkboxWidgetClass = (WidgetClass) &checkboxClassRec; + + + + + + +/**************************************************************** + * + * Class Methods + * + ****************************************************************/ + +static void +CheckboxClassInit (void) +{ + XawInitializeWidgetSet(); +} + + +/*ARGSUSED*/ +static void +CheckboxInit (Widget request, + Widget new, + ArgList args, + Cardinal *num_args) +{ +#if DRAW_CHECK + CheckboxWidget cw = (CheckboxWidget) new; + cw->checkbox.checkmark = None ; + cw->checkbox.checkmark_GC = None ; +#endif +} + + +#if DRAW_CHECK +static void +CheckboxRealize(Widget w, + Mask *valueMask, + XSetWindowAttributes *attributes) +{ + CheckboxWidget cw = (CheckboxWidget) w; + XtGCMask value_mask, dynamic_mask, dontcare_mask ; + XGCValues values ; + + /* first, call superclass realize */ + (*checkboxWidgetClass->core_class.superclass->core_class.realize) + (w, valueMask, attributes); + + /* TODO: cache this via xmu */ + if( cw->checkbox.checkmark == None ) + cw->checkbox.checkmark = + XCreateBitmapFromData( XtDisplay(w), XtWindow(w), + check_bits,check_width,check_height); + + values.fill_style = FillStippled ; + values.stipple = cw->checkbox.checkmark ; + values.foreground = cw->label.foreground ; + value_mask = GCFillStyle | GCStipple | GCForeground ; + dynamic_mask = GCTileStipXOrigin | GCTileStipYOrigin ; + dontcare_mask = GCLineWidth | GCLineStyle | GCCapStyle | GCJoinStyle | + GCFont | GCSubwindowMode | GCGraphicsExposures | + GCDashOffset | GCDashList | GCArcMode ; + cw->checkbox.checkmark_GC = + XtAllocateGC(w, 0, value_mask, &values, dynamic_mask, dontcare_mask) ; +} +#endif + + +/* Function Name: CheckboxDestroy + * Description: Destroy Callback for checkbox widget. + * Arguments: w - the checkbox widget that is being destroyed. + * junk, grabage - not used. + * Returns: none. + */ + +/* ARGSUSED */ +static void +CheckboxDestroy (Widget w, + XtPointer junk, + XtPointer garbage) +{ +#if DRAW_CHECK + CheckboxWidget cw = (CheckboxWidget) w; + + /* TODO: cache this via xmu */ + if( cw->checkbox.checkmark != None ) + XFreePixmap( XtDisplay(w), cw->checkbox.checkmark ) ; + if( cw->checkbox.checkmark_GC != None ) + XtReleaseGC(w, cw->checkbox.checkmark_GC) ; +#endif +} + + + +#if DRAW_CHECK +/************************************************************ + * + * Actions Procedures + * + ************************************************************/ + +/* ARGSUSED */ +static void +CheckboxPress (Widget w, + XEvent *event, + String *params, /* unused */ + Cardinal *num_params) /* unused */ +{ + CheckboxWidget cw = (CheckboxWidget) w ; + if( !cw->checkbox.pressed ) { + cw->checkbox.pressed = TRUE ; + ((CheckboxWidgetClass)(w->core.widget_class))->radio_class.drawDiamond(w) ; + } +} + +static void +CheckboxUnpress (Widget w, + XEvent *event, + String *params, /* unused */ + Cardinal *num_params) /* unused */ +{ + CheckboxWidget cw = (CheckboxWidget) w ; + int i ; + + if( cw->checkbox.pressed ) { + cw->checkbox.pressed = FALSE ; + if( *num_params > 0 && **params == 'd' ) + ((CheckboxWidgetClass)(w->core.widget_class))->radio_class.drawDiamond(w); + } +} +#endif + + + + + +/************************************************************ + * + * Internal Procedures + * + ************************************************************/ + +static void +DrawCheck (Widget w) +{ + CheckboxWidget cw = (CheckboxWidget) w ; + Display *dpy = XtDisplay(w) ; + Window win = XtWindow(w) ; + GC gc ; + +#ifdef _ThreeDP_h + XPoint pts[6] ; +#endif + Dimension s = swid(cw); + Dimension bsz = bsize(cw); + Position bx,by ; /* Check upper-left */ + Dimension bw,bh ; +#ifdef _ThreeDP_h + GC top, bot; +#endif + GC ctr ; + + /* foreground GC */ + gc = XtIsSensitive(w) ? cw->command.normal_GC : cw->label.gray_GC ; + + bw = bh = bs(cw) ; + bx = cw->label.internal_width ; + by = cw->core.height/2 - bh/2 ; + +#ifdef _ThreeDP_h + if( !cw->command.set ) { + top = cw->threeD.top_shadow_GC ; + bot = cw->threeD.bot_shadow_GC ; + } else { + top = cw->threeD.bot_shadow_GC ; + bot = cw->threeD.top_shadow_GC ; + } + ctr = cw->command.inverse_GC ; +#else + ctr = cw->command.set ? cw->command.normal_GC : cw->command.inverse_GC ; +#endif + + XFillRectangle(dpy,win,ctr, bx+s,by+s, bsz,bsz) ; + +#ifdef _ThreeDP_h + /* top-left shadow */ + pts[0].x = bx ; pts[0].y = by ; + pts[1].x = bw ; pts[1].y = 0 ; + pts[2].x = -s ; pts[2].y = s ; + pts[3].x = -bsz ; pts[3].y = 0 ; + pts[4].x = 0 ; pts[4].y = bsz ; + pts[5].x = -s ; pts[5].y = s ; + XFillPolygon(dpy,win,top, pts,6, Nonconvex,CoordModePrevious) ; + /* bottom-right shadow */ + pts[0].x = bx+bw ; pts[0].y = by+bh ; + pts[1].x = -bw ; pts[1].y = 0 ; + pts[2].x = s ; pts[2].y = -s ; + pts[3].x = bsz ; pts[3].y = 0 ; + pts[4].x = 0 ; pts[4].y = -bsz ; + pts[5].x = s ; pts[5].y = -s ; + XFillPolygon(dpy,win,bot, pts,6, Nonconvex,CoordModePrevious) ; +#else + XDrawRectangle(dpy,win,gc, bx+s,by+s, bsz,bsz) ; +#endif + +#if DRAW_CHECK + if( cw->command.set && cw->checkbox.checkmark_GC != None ) { + XSetTSOrigin(dpy,cw->checkbox.checkmark_GC, bx+s, by+s) ; + XFillRectangle(dpy,win,cw->checkbox.checkmark_GC, + bx+s, by+s, check_width,check_height) ; + } +#endif +} diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwcheckbox.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwcheckbox.h Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,103 @@ +/* Checkbox Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* Synched up with: Checkbox.h 1.1 */ + +/* + * Checkbox.h - Checkbox widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: June 30, 1997 + */ + +#ifndef _XawCheckbox_h +#define _XawCheckbox_h + +/*********************************************************************** + * + * Checkbox Widget + * + * The Checkbox widget is identical to the Radio widget in behavior but + * not in appearance. The Checkbox widget looks like a small diamond + * shaped button to the left of the label. + * + ***********************************************************************/ + +#include "xlwradio.h" + +/* Resources: + + Name Class RepType Default Value + ---- ----- ------- ------------- + tristate Tristate Boolean FALSE + + radioGroup RadioGroup Widget NULL + radioData RadioData Pointer (XPointer) Widget + state State Boolean Off + background Background Pixel XtDefaultBackground + bitmap Pixmap Pixmap None + border BorderColor Pixel XtDefaultForeground + borderWidth BorderWidth Dimension 1 + callback Callback Pointer NULL + cursor Cursor Cursor None + destroyCallback Callback Pointer NULL + font Font XFontStructx* XtDefaultFont + foreground Foreground Pixel XtDefaultForeground + height Height Dimension text height + highlightThickness Thickness Dimension 2 + insensitiveBorder sensitive Pixmap Gray + internalHeight Height Dimension 2 + internalWidth Width Dimension 4 + justify Justify XtJustify XtJustifyCenter + label Label String NULL + mappedWhenManaged MappedWhenManaged Boolean True + resize Resize Boolean True + sensitive Sensitive Boolean True + width Width Dimension text width + x Position Position 0 + y Position Position 0 + +*/ + +/* + * These should be in StringDefs.h but aren't so we will define + * them here if they are needed. + */ + + +#define XtCTristate "Tristate" + +#define XtNtristate "tristate" + +extern WidgetClass checkboxWidgetClass; + +typedef struct _CheckboxClassRec *CheckboxWidgetClass; +typedef struct _CheckboxRec *CheckboxWidget; + + +/************************************************************ + * + * Public Functions + * + ************************************************************/ + +#endif /* _XawCheckbox_h */ diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwcheckboxP.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwcheckboxP.h Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,95 @@ +/* Checkbox Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* + * CheckboxP.h - Private definitions for Checkbox widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: June 30, 1997 + */ + +#ifndef _XawCheckboxP_h +#define _XawCheckboxP_h + +#include "xlwcheckbox.h" +#include "xlwradioP.h" + +/************************************ + * + * Class structure + * + ***********************************/ + + /* New fields for the Checkbox widget class record */ +typedef struct _CheckboxClass { + XtPointer extension; +} CheckboxClassPart; + + /* Full class record declaration */ +typedef struct _CheckboxClassRec { + CoreClassPart core_class; + SimpleClassPart simple_class; +#ifdef _ThreeDP_h + ThreeDClassPart threeD_class; +#endif + LabelClassPart label_class; + CommandClassPart command_class; + ToggleClassPart toggle_class; + RadioClassPart radio_class; + CheckboxClassPart checkbox_class; +} CheckboxClassRec; + +extern CheckboxClassRec checkboxClassRec; + +/*************************************** + * + * Instance (widget) structure + * + **************************************/ + + /* New fields for the Checkbox widget record */ +typedef struct { + /* resources */ + Boolean tristate ; + + /* private data */ + Boolean pressed ; + Pixmap checkmark ; /* TODO: share these via xmu? */ + GC checkmark_GC ; + XtPointer extension; +} CheckboxPart; + + /* Full widget declaration */ +typedef struct _CheckboxRec { + CorePart core; + SimplePart simple; +#ifdef _ThreeDP_h + ThreeDPart threeD; +#endif + LabelPart label; + CommandPart command; + TogglePart toggle; + RadioPart radio; + CheckboxPart checkbox; +} CheckboxRec; + +#endif /* _XawCheckboxP_h */ diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwgauge.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwgauge.c Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,1138 @@ +/* Gauge Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* Synched up with: Gauge.c 1.2 */ + +/* + * Gauge.c - Gauge widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: July 9, 1997 + * + * Note: for fun and demonstration purposes, I have added selection + * capabilities to this widget. If you select the widget, you create + * a primary selection containing the current value of the widget in + * both integer and string form. If you copy into the widget, the + * primary selection is converted to an integer value and the gauge is + * set to that value. + */ + +/* TODO: display time instead of value + */ + +#define DEF_LEN 50 /* default width (or height for vertical gauge) */ +#define MIN_LEN 10 /* minimum reasonable width (height) */ +#define TIC_LEN 6 /* length of tic marks */ +#define GA_WID 3 /* width of gauge */ +#define MS_PER_SEC 1000 + +#include +#include +#include +#include +#include +#include +#include +#include +#include "xlwgaugeP.h" +#include "../src/xmu.h" +#ifdef HAVE_XMU +#include +#include +#include +#endif + + +/**************************************************************** + * + * Gauge resources + * + ****************************************************************/ + + +static char defaultTranslations[] = + ": select()\n\ + F1: select(CLIPBOARD)\n\ + : paste()\n\ + F2: paste(CLIPBOARD)" ; + + + +#define offset(field) XtOffsetOf(GaugeRec, field) +static XtResource resources[] = { + {XtNvalue, XtCValue, XtRInt, sizeof(int), + offset(gauge.value), XtRImmediate, (XtPointer)0}, + {XtNminValue, XtCMinValue, XtRInt, sizeof(int), + offset(gauge.v0), XtRImmediate, (XtPointer)0}, + {XtNmaxValue, XtCMaxValue, XtRInt, sizeof(int), + offset(gauge.v1), XtRImmediate, (XtPointer)100}, + {XtNntics, XtCNTics, XtRInt, sizeof(int), + offset(gauge.ntics), XtRImmediate, (XtPointer) 0}, + {XtNnlabels, XtCNLabels, XtRInt, sizeof(int), + offset(gauge.nlabels), XtRImmediate, (XtPointer) 0}, + {XtNlabels, XtCLabels, XtRStringArray, sizeof(String *), + offset(gauge.labels), XtRStringArray, NULL}, + {XtNautoScaleUp, XtCAutoScaleUp, XtRBoolean, sizeof(Boolean), + offset(gauge.autoScaleUp), XtRImmediate, FALSE}, + {XtNautoScaleDown, XtCAutoScaleDown, XtRBoolean, sizeof(Boolean), + offset(gauge.autoScaleDown), XtRImmediate, FALSE}, + {XtNorientation, XtCOrientation, XtROrientation, sizeof(XtOrientation), + offset(gauge.orientation), XtRImmediate, (XtPointer)XtorientHorizontal}, + {XtNupdate, XtCInterval, XtRInt, sizeof(int), + offset(gauge.update), XtRImmediate, (XtPointer)0}, + {XtNgetValue, XtCCallback, XtRCallback, sizeof(XtPointer), + offset(gauge.getValue), XtRImmediate, (XtPointer)NULL}, +}; +#undef offset + + + + /* member functions */ + +static void GaugeClassInit (void); +static void GaugeInit (Widget, Widget, ArgList, Cardinal *); +static void GaugeDestroy (Widget); +static void GaugeResize (Widget); +static void GaugeExpose (Widget, XEvent *, Region); +static Boolean GaugeSetValues (Widget, Widget, Widget, ArgList, Cardinal *); +static XtGeometryResult GaugeQueryGeometry (Widget, XtWidgetGeometry *, + XtWidgetGeometry *); + + /* action procs */ + +static void GaugeSelect (Widget, XEvent *, String *, Cardinal *); +static void GaugePaste (Widget, XEvent *, String *, Cardinal *); + + /* internal privates */ + +static void GaugeSize (GaugeWidget, Dimension *, Dimension *, Dimension); +static void MaxLabel (GaugeWidget, Dimension *, Dimension *, + Dimension *, Dimension *); +static void AutoScale (GaugeWidget); +static void EnableUpdate (GaugeWidget); +static void DisableUpdate (GaugeWidget); + +static void GaugeGetValue (XtPointer, XtIntervalId *); +static void GaugeMercury (Display *, Window, GC, GaugeWidget, Cardinal, Cardinal); + +static Boolean GaugeConvert (Widget, Atom *, Atom *, Atom *, + XtPointer *, u_long *, int *); +static void GaugeLoseSel (Widget, Atom *); +static void GaugeDoneSel (Widget, Atom *, Atom *); +static void GaugeGetSelCB (Widget, XtPointer, Atom *, Atom *, + XtPointer, u_long *, int *); + +static GC Get_GC (GaugeWidget, Pixel); + + +static XtActionsRec actionsList[] = +{ + {"select", GaugeSelect}, + {"paste", GaugePaste}, +} ; + + + +/**************************************************************** + * + * Full class record constant + * + ****************************************************************/ + +GaugeClassRec gaugeClassRec = { + { +/* core_class fields */ + /* superclass */ (WidgetClass) &labelClassRec, + /* class_name */ "Gauge", + /* widget_size */ sizeof(GaugeRec), + /* class_initialize */ GaugeClassInit, + /* class_part_initialize */ NULL, + /* class_inited */ FALSE, + /* initialize */ GaugeInit, + /* initialize_hook */ NULL, + /* realize */ XtInheritRealize, /* TODO? */ + /* actions */ actionsList, + /* num_actions */ XtNumber(actionsList), + /* resources */ resources, + /* num_resources */ XtNumber(resources), + /* xrm_class */ NULLQUARK, + /* compress_motion */ TRUE, + /* compress_exposure */ TRUE, + /* compress_enterleave */ TRUE, + /* visible_interest */ FALSE, + /* destroy */ GaugeDestroy, + /* resize */ GaugeResize, + /* expose */ GaugeExpose, + /* set_values */ GaugeSetValues, + /* set_values_hook */ NULL, + /* set_values_almost */ XtInheritSetValuesAlmost, + /* get_values_hook */ NULL, + /* accept_focus */ NULL, + /* version */ XtVersion, + /* callback_private */ NULL, + /* tm_table */ defaultTranslations, + /* query_geometry */ GaugeQueryGeometry, + /* display_accelerator */ XtInheritDisplayAccelerator, + /* extension */ NULL + }, +/* Simple class fields initialization */ + { + /* change_sensitive */ XtInheritChangeSensitive + }, +#ifdef _ThreeDP_h +/* ThreeD class fields initialization */ + { + XtInheritXaw3dShadowDraw /* shadowdraw */ + }, +#endif +/* Label class fields initialization */ + { + /* ignore */ 0 + }, +/* Gauge class fields initialization */ + { + /* extension */ NULL + }, +}; + +WidgetClass gaugeWidgetClass = (WidgetClass)&gaugeClassRec; + + + + +/**************************************************************** + * + * Member Procedures + * + ****************************************************************/ + +static void +GaugeClassInit (void) +{ + XawInitializeWidgetSet(); +#ifdef HAVE_XMU + XtAddConverter(XtRString, XtROrientation, XmuCvtStringToOrientation, + NULL, 0) ; +#endif +} + + + +/* ARGSUSED */ +static void +GaugeInit (Widget request, + Widget new, + ArgList args, + Cardinal *num_args) +{ + GaugeWidget gw = (GaugeWidget) new; + + if( gw->gauge.v0 == 0 && gw->gauge.v1 == 0 ) { + gw->gauge.autoScaleUp = gw->gauge.autoScaleDown = TRUE ; + AutoScale(gw) ; + } + + /* If size not explicitly set, set it to our preferred size now. */ + + if( request->core.width == 0 || request->core.height == 0 ) + { + Dimension w,h ; + GaugeSize(gw, &w,&h, DEF_LEN) ; + if( request->core.width == 0 ) + new->core.width = w ; + if( request->core.height == 0 ) + new->core.height = h ; + gw->core.widget_class->core_class.resize(new) ; + } + + gw->gauge.selected = None ; + gw->gauge.selstr = NULL ; + + if( gw->gauge.update > 0 ) + EnableUpdate(gw) ; + + gw->gauge.inverse_GC = Get_GC(gw, gw->core.background_pixel) ; +} + +static void +GaugeDestroy (Widget w) +{ + GaugeWidget gw = (GaugeWidget)w; + + if( gw->gauge.selstr != NULL ) + XtFree(gw->gauge.selstr) ; + + if( gw->gauge.selected != None ) + XtDisownSelection(w, gw->gauge.selected, CurrentTime) ; + + XtReleaseGC(w, gw->gauge.inverse_GC) ; + + if( gw->gauge.update > 0 ) + DisableUpdate(gw) ; +} + + +/* React to size change from manager. Label widget will compute some + * internal stuff, but we need to override. + */ + +static void +GaugeResize (Widget w) +{ + GaugeWidget gw = (GaugeWidget)w; + int size ; /* height (width) of gauge */ + int vmargin ; /* vertical (horizontal) margin */ + int hmargin ; /* horizontal (vertical) margin */ + + vmargin = gw->gauge.orientation == XtorientHorizontal ? + gw->label.internal_height : gw->label.internal_width ; + hmargin = gw->gauge.orientation == XtorientHorizontal ? + gw->label.internal_width : gw->label.internal_height ; + + /* TODO: need to call parent resize proc? I don't think so since + * we're recomputing everything from scratch anyway. + */ + + /* find total height (width) of contents */ + + size = GA_WID+2 ; /* gauge itself + edges */ + + if( gw->gauge.ntics > 1 ) /* tic marks */ + size += vmargin + TIC_LEN ; + + if( gw->gauge.nlabels > 1 ) + { + Dimension lwm, lw0, lw1 ; /* width of max, left, right labels */ + Dimension lh ; + + MaxLabel(gw,&lwm,&lh, &lw0,&lw1) ; + + if( gw->gauge.orientation == XtorientHorizontal ) + { + gw->gauge.margin0 = lw0 / 2 ; + gw->gauge.margin1 = lw1 / 2 ; + size += lh + vmargin ; + } + else + { + gw->gauge.margin0 = + gw->gauge.margin1 = lh / 2 ; + size += lwm + vmargin ; + } + } + else + gw->gauge.margin0 = gw->gauge.margin1 = 0 ; + + gw->gauge.margin0 += hmargin ; + gw->gauge.margin1 += hmargin ; + + /* Now distribute height (width) over components */ + + if( gw->gauge.orientation == XtorientHorizontal ) + gw->gauge.gmargin = (gw->core.height-size)/2 ; + else + gw->gauge.gmargin = (gw->core.width-size)/2 ; + + gw->gauge.tmargin = gw->gauge.gmargin + GA_WID+2 + vmargin ; + if( gw->gauge.ntics > 1 ) + gw->gauge.lmargin = gw->gauge.tmargin + TIC_LEN + vmargin ; + else + gw->gauge.lmargin = gw->gauge.tmargin ; +} + +/* + * Repaint the widget window + */ + +/* ARGSUSED */ +static void +GaugeExpose (Widget w, + XEvent *event, + Region region) +{ + GaugeWidget gw = (GaugeWidget) w; +register Display *dpy = XtDisplay(w) ; +register Window win = XtWindow(w) ; + GC gc; /* foreground, background */ + GC gctop, gcbot ; /* dark, light shadows */ + + int len ; /* length (width or height) of widget */ + int hgt ; /* height (width) of widget */ + int e0,e1 ; /* ends of the gauge */ + int x ; + int y ; /* vertical (horizontal) position */ + int i ; + int v0 = gw->gauge.v0 ; + int v1 = gw->gauge.v1 ; + int value = gw->gauge.value ; + + gc = XtIsSensitive(w) ? gw->label.normal_GC : gw->label.gray_GC ; + + +#ifdef _ThreeDP_h + gctop = gw->threeD.bot_shadow_GC ; + gcbot = gw->threeD.top_shadow_GC ; +#else + gctop = gcbot = gc ; +#endif + + if( gw->gauge.orientation == XtorientHorizontal ) { + len = gw->core.width ; + hgt = gw->core.height ; + } else { + len = gw->core.height ; + hgt = gw->core.width ; + } + + /* if the gauge is selected, signify by drawing the background + * in a constrasting color. + */ + + if( gw->gauge.selected ) + { + XFillRectangle(dpy,win, gc, 0,0, w->core.width,w->core.height) ; + gc = gw->gauge.inverse_GC ; + } + + e0 = gw->gauge.margin0 ; /* left (top) end */ + e1 = len - gw->gauge.margin1 -1 ; /* right (bottom) end */ + + /* Draw the Gauge itself */ + + y = gw->gauge.gmargin ; + + if( gw->gauge.orientation == XtorientHorizontal ) /* horizontal */ + { + XDrawLine(dpy,win,gctop, e0+1,y, e1-1,y) ; + XDrawLine(dpy,win,gctop, e0,y+1, e0,y+GA_WID) ; + XDrawLine(dpy,win,gcbot, e0+1, y+GA_WID+1, e1-1, y+GA_WID+1) ; + XDrawLine(dpy,win,gcbot, e1,y+1, e1,y+GA_WID) ; + } + else /* vertical */ + { + XDrawLine(dpy,win,gctop, y,e0+1, y,e1-1) ; + XDrawLine(dpy,win,gctop, y+1,e0, y+GA_WID,e0) ; + XDrawLine(dpy,win,gcbot, y+GA_WID+1,e0+1, y+GA_WID+1, e1-1) ; + XDrawLine(dpy,win,gcbot, y+1,e1, y+GA_WID,e1) ; + } + + + /* draw the mercury */ + + GaugeMercury(dpy, win, gc, gw, 0,value) ; + + + if( gw->gauge.ntics > 1 ) + { + y = gw->gauge.tmargin ; + for(i=0; igauge.ntics; ++i) + { + x = e0 + i*(e1-e0-1)/(gw->gauge.ntics-1) ; + if( gw->gauge.orientation == XtorientHorizontal ) { + XDrawLine(dpy,win,gcbot, x,y+1, x,y+TIC_LEN-2) ; + XDrawLine(dpy,win,gcbot, x,y, x+1,y) ; + XDrawLine(dpy,win,gctop, x+1,y+1, x+1,y+TIC_LEN-2) ; + XDrawLine(dpy,win,gctop, x,y+TIC_LEN-1, x+1,y+TIC_LEN-1) ; + } + else { + XDrawLine(dpy,win,gcbot, y+1,x, y+TIC_LEN-2,x) ; + XDrawLine(dpy,win,gcbot, y,x, y,x+1) ; + XDrawLine(dpy,win,gctop, y+1,x+1, y+TIC_LEN-2,x+1) ; + XDrawLine(dpy,win,gctop, y+TIC_LEN-1,x, y+TIC_LEN-1,x+1) ; + } + } + } + + /* draw labels */ + if( gw->gauge.nlabels > 1 ) + { + char label[20], *s = label ; + int len, w,h =0 ; + + if( gw->gauge.orientation == XtorientHorizontal ) + y = gw->gauge.lmargin + gw->label.font->max_bounds.ascent - 1 ; + else { + y = gw->gauge.lmargin ; + h = gw->label.font->max_bounds.ascent / 2 ; + } + + for(i=0; igauge.nlabels; ++i) + { + if( gw->gauge.labels == NULL ) + sprintf(label, "%d", v0+i*(v1 - v0)/(gw->gauge.nlabels - 1)) ; + else + s = gw->gauge.labels[i] ; + if( s != NULL ) { + x = e0 + i*(e1-e0-1)/(gw->gauge.nlabels-1) ; + len = strlen(s) ; + if( gw->gauge.orientation == XtorientHorizontal ) { + w = XTextWidth(gw->label.font, s, len) ; + XDrawString(dpy,win,gc, x-w/2,y, s,len) ; + } + else { + XDrawString(dpy,win,gc, y,x+h, s,len) ; + } + } + } + } +} + + +/* + * Set specified arguments into widget + */ + +static Boolean +GaugeSetValues (Widget old, + Widget request, + Widget new, + ArgList args, + Cardinal *num_args) +{ + GaugeWidget oldgw = (GaugeWidget) old; + GaugeWidget gw = (GaugeWidget) new; + Boolean was_resized = False; + + if( gw->gauge.selected != None ) { + XtDisownSelection(new, gw->gauge.selected, CurrentTime) ; + gw->gauge.selected = None ; + } + + /* Changes to v0,v1,labels, ntics, nlabels require resize & redraw. */ + /* Change to value requires redraw and possible resize if autoscale */ + + was_resized = + gw->gauge.v0 != oldgw->gauge.v0 || + gw->gauge.v1 != oldgw->gauge.v1 || + gw->gauge.ntics != oldgw->gauge.ntics || + gw->gauge.nlabels != oldgw->gauge.nlabels || + gw->gauge.labels != oldgw->gauge.labels ; + + if( (gw->gauge.autoScaleUp && gw->gauge.value > gw->gauge.v1) || + (gw->gauge.autoScaleDown && gw->gauge.value < gw->gauge.v1/3 )) + { + AutoScale(gw) ; + was_resized = TRUE ; + } + + if( was_resized ) { + if( gw->label.resize ) + GaugeSize(gw, &gw->core.width, &gw->core.height, DEF_LEN) ; + else + GaugeResize(new) ; + } + + if( gw->gauge.update != oldgw->gauge.update ) + { + if( gw->gauge.update > 0 ) + EnableUpdate(gw) ; + else + DisableUpdate(gw) ; + } + + if( gw->core.background_pixel != oldgw->core.background_pixel ) + { + XtReleaseGC(new, gw->gauge.inverse_GC) ; + gw->gauge.inverse_GC = Get_GC(gw, gw->core.background_pixel) ; + } + + return was_resized || gw->gauge.value != oldgw->gauge.value || + XtIsSensitive(old) != XtIsSensitive(new); +} + + +static XtGeometryResult +GaugeQueryGeometry (Widget w, + XtWidgetGeometry *intended, + XtWidgetGeometry *preferred) +{ + register GaugeWidget gw = (GaugeWidget)w; + + if( intended->width == w->core.width && + intended->height == w->core.height ) + return XtGeometryNo ; + + preferred->request_mode = CWWidth | CWHeight; + GaugeSize(gw, &preferred->width, &preferred->height, DEF_LEN) ; + + if( (!(intended->request_mode & CWWidth) || + intended->width >= preferred->width) && + (!(intended->request_mode & CWHeight) || + intended->height >= preferred->height) ) + return XtGeometryYes; + else + return XtGeometryAlmost; +} + + + + +/**************************************************************** + * + * Action Procedures + * + ****************************************************************/ + +static void +GaugeSelect (Widget w, + XEvent *event, + String *params, + Cardinal *num_params) +{ + GaugeWidget gw = (GaugeWidget)w ; + Atom seln = XA_PRIMARY ; + + if( gw->gauge.selected != None ) { + XtDisownSelection(w, gw->gauge.selected, CurrentTime) ; + gw->gauge.selected = None ; + } + + if( *num_params > 0 ) { + seln = XInternAtom(XtDisplay(w), params[0], False) ; + printf("atom %s is %ld\n", params[0], seln) ; + } + + if( ! XtOwnSelection(w, seln, event->xbutton.time, GaugeConvert, + GaugeLoseSel, GaugeDoneSel) ) + { + /* in real code, this error message would be replaced by + * something more elegant, or at least deleted + */ + + fprintf(stderr, "Gauge failed to get selection, try again\n") ; + } + else + { + gw->gauge.selected = TRUE ; + gw->gauge.selstr = (String)XtMalloc(4*sizeof(int)) ; + sprintf(gw->gauge.selstr, "%d", gw->gauge.value) ; + GaugeExpose(w,0,0) ; + } +} + + +static Boolean +GaugeConvert (Widget w, + Atom *selection, /* usually XA_PRIMARY */ + Atom *target, /* requested target */ + Atom *type, /* returned type */ + XtPointer *value, /* returned value */ + u_long *length, /* returned length */ + int *format) /* returned format */ +{ + GaugeWidget gw = (GaugeWidget)w ; + XSelectionRequestEvent *req ; + + printf( "requesting selection %s:%s\n", + XGetAtomName(XtDisplay(w),*selection), + XGetAtomName(XtDisplay(w),*target)); + +#ifdef HAVE_XMU + if( *target == XA_TARGETS(XtDisplay(w)) ) + { + Atom *rval, *stdTargets ; + u_long stdLength ; + + /* XmuConvertStandardSelection can handle this. This function + * will return a list of standard targets. We prepend TEXT, + * STRING and INTEGER to the list and return it. + */ + + req = XtGetSelectionRequest(w, *selection, NULL) ; + XmuConvertStandardSelection(w, req->time, selection, target, + type, (XPointer*)&stdTargets, &stdLength, format) ; + + *type = XA_ATOM ; /* TODO: needed? */ + *length = stdLength + 3 ; + rval = (Atom *) XtMalloc(sizeof(Atom)*(stdLength+3)) ; + *value = (XtPointer) rval ; + *rval++ = XA_INTEGER ; + *rval++ = XA_STRING ; + *rval++ = XA_TEXT(XtDisplay(w)) ; + bcopy((char *)stdTargets, (char *)rval, stdLength*sizeof(Atom)) ; + XtFree((char*) stdTargets) ; + *format = 8*sizeof(Atom) ; /* TODO: needed? */ + return True ; + } + + else +#endif + if( *target == XA_INTEGER ) + { + *type = XA_INTEGER ; + *length = 1 ; + *value = (XtPointer) &gw->gauge.value ; + *format = 8*sizeof(int) ; + return True ; + } + + else if( *target == XA_STRING +#ifdef HAVE_XMU + || + *target == XA_TEXT(XtDisplay(w)) +#endif + ) + { + *type = *target ; + *length = strlen(gw->gauge.selstr)*sizeof(char) ; + *value = (XtPointer) gw->gauge.selstr ; + *format = 8 ; + return True ; + } + + else + { + /* anything else, we just give it to XmuConvertStandardSelection() */ +#ifdef HAVE_XMU + req = XtGetSelectionRequest(w, *selection, NULL) ; + if( XmuConvertStandardSelection(w, req->time, selection, target, + type, (XPointer *) value, length, format) ) + return True ; + else +#endif + { + printf( + "Gauge: requestor is requesting unsupported selection %s:%s\n", + XGetAtomName(XtDisplay(w),*selection), + XGetAtomName(XtDisplay(w),*target)); + return False ; + } + } +} + + + +static void +GaugeLoseSel (Widget w, + Atom *selection) /* usually XA_PRIMARY */ +{ + GaugeWidget gw = (GaugeWidget)w ; + Display *dpy = XtDisplay(w) ; + Window win = XtWindow(w) ; + + if( gw->gauge.selstr != NULL ) { + XtFree(gw->gauge.selstr) ; + gw->gauge.selstr = NULL ; + } + + gw->gauge.selected = False ; + XClearWindow(dpy,win) ; + GaugeExpose(w,0,0) ; +} + + +static void +GaugeDoneSel (Widget w, + Atom *selection, /* usually XA_PRIMARY */ + Atom *target) /* requested target */ +{ + /* selection done, anything to do? */ +} + + +static void +GaugePaste (Widget w, + XEvent *event, + String *params, + Cardinal *num_params) +{ + Atom seln = XA_PRIMARY ; + + if( *num_params > 0 ) { + seln = XInternAtom(XtDisplay(w), params[0], False) ; + printf("atom %s is %ld\n", params[0], seln) ; + } + + /* try for integer value first */ + XtGetSelectionValue(w, seln, XA_INTEGER, + GaugeGetSelCB, (XtPointer)XA_INTEGER, + event->xbutton.time) ; +} + +static void +GaugeGetSelCB (Widget w, + XtPointer client, + Atom *selection, + Atom *type, + XtPointer value, + u_long *length, + int *format) +{ + Display *dpy = XtDisplay(w) ; + Atom target = (Atom)client ; + int *iptr ; + char *cptr ; + + if( *type == XA_INTEGER ) { + iptr = (int *)value ; + XawGaugeSetValue(w, *iptr) ; + } + + else if( *type == XA_STRING +#ifdef HAVE_XMU + || + *type == XA_TEXT(dpy) +#endif + ) + { + cptr = (char *)value ; + XawGaugeSetValue(w, atoi(cptr)) ; + } + + /* failed, try string */ + else if( *type == None && target == XA_INTEGER ) + XtGetSelectionValue(w, *selection, XA_STRING, + GaugeGetSelCB, (XtPointer)XA_STRING, + CurrentTime) ; +} + + + +/**************************************************************** + * + * Public Procedures + * + ****************************************************************/ + + + /* Change gauge value. Only undraw or draw what needs to be + * changed. + */ + +void +XawGaugeSetValue (Widget w, + Cardinal value) +{ + GaugeWidget gw = (GaugeWidget)w ; + int oldvalue ; + GC gc ; + + if( gw->gauge.selected != None ) { + XtDisownSelection(w, gw->gauge.selected, CurrentTime) ; + gw->gauge.selected = None ; + } + + if( !XtIsRealized(w) ) { + gw->gauge.value = value ; + return ; + } + + /* need to rescale? */ + if(( gw->gauge.autoScaleUp && value > gw->gauge.v1) || + (gw->gauge.autoScaleDown && value < gw->gauge.v1/3 )) + { + XtVaSetValues(w, XtNvalue, value, 0) ; + return ; + } + + oldvalue = gw->gauge.value ; + gw->gauge.value = value ; + + gc = XtIsSensitive(w) ? gw->label.normal_GC : gw->label.gray_GC ; + GaugeMercury(XtDisplay(w), XtWindow(w), gc, gw, oldvalue,value) ; +} + + +Cardinal +XawGaugeGetValue (Widget w) +{ + GaugeWidget gw = (GaugeWidget)w ; + return gw->gauge.value ; +} + + + + +/**************************************************************** + * + * Private Procedures + * + ****************************************************************/ + + /* draw the mercury over a specific region */ + +static void +GaugeMercury (Display *dpy, + Window win, + GC gc, + GaugeWidget gw, + Cardinal val0, + Cardinal val1) +{ + int v0 = gw->gauge.v0 ; + int v1 = gw->gauge.v1 ; + int vd = v1 - v0 ; + Dimension len ; /* length (width or height) of gauge */ + Position e0, e1 ; /* gauge ends */ + Position p0, p1 ; /* mercury ends */ + int y ; /* vertical (horizontal) position */ + Boolean undraw = FALSE ; + + len = gw->gauge.orientation == XtorientHorizontal ? + gw->core.width : gw->core.height ; + + e0 = gw->gauge.margin0 ; /* left (top) end */ + e1 = len - gw->gauge.margin1 -1 ; /* right (bottom) end */ + + if( vd <= 0 ) vd = 1 ; + + if( val0 < v0 ) val0 = v0 ; + else if( val0 > v1 ) val0 = v1 ; + if( val1 < v0 ) val1 = v0 ; + else if( val1 > v1 ) val1 = v1 ; + + p0 = (val0-v0)*(e1-e0-1)/vd ; + p1 = (val1-v0)*(e1-e0-1)/vd ; + + if( p1 == p0 ) + return ; + + y = gw->gauge.gmargin ; + + if( p1 < p0 ) + { + Position tmp = p0 ; + p0 = p1 ; + p1 = tmp ; + gc = gw->label.normal_GC ; + XSetForeground(dpy,gc, gw->core.background_pixel) ; + undraw = TRUE ; + } + + if( gw->gauge.orientation == XtorientHorizontal ) + XFillRectangle(dpy,win,gc, e0+p0+1,y+1, p1-p0,GA_WID) ; + else + XFillRectangle(dpy,win,gc, y+1,e1-p1, GA_WID,p1-p0) ; + + if( undraw ) + XSetForeground(dpy,gc, gw->label.foreground) ; +} + + + +/* Search the labels, find the largest one. */ +/* TODO: handle vertical fonts? */ + +static void +MaxLabel (GaugeWidget gw, + Dimension *wid, /* max label width */ + Dimension *hgt, /* max label height */ + Dimension *w0, /* width of first label */ + Dimension *w1) /* width of last label */ +{ + char lstr[80], *lbl ; + int w ; + XFontStruct *font = gw->label.font ; + int i ; + int lw = 0; + int v0 = gw->gauge.v0 ; + int dv = gw->gauge.v1 - v0 ; + int n = gw->gauge.nlabels ; + + if( n > 0 ) + { + if( --n <= 0 ) {n = 1 ; v0 += dv/2 ;} + + /* loop through all labels, figure out how much room they + * need. + */ + w = 0 ; + for(i=0; igauge.nlabels; ++i) + { + if( gw->gauge.labels == NULL ) /* numeric labels */ + sprintf(lbl = lstr,"%d", v0 + i*dv/n) ; + else + lbl = gw->gauge.labels[i] ; + + if( lbl != NULL ) { + lw = XTextWidth(font, lbl, strlen(lbl)) ; + w = Max( w, lw ) ; + } + else + lw = 0 ; + + if( i == 0 && w0 != NULL ) *w0 = lw ; + } + if( w1 != NULL ) *w1 = lw ; + + *wid = w ; + *hgt = font->max_bounds.ascent + font->max_bounds.descent ; + } + else + *wid = *hgt = 0 ; +} + + +/* Determine the preferred size for this widget. choose 100x100 for + * debugging. + */ + +static void +GaugeSize (GaugeWidget gw, + Dimension *wid, + Dimension *hgt, + Dimension min_len) +{ + int w,h ; /* width, height of gauge */ + int vmargin ; /* vertical margin */ + int hmargin ; /* horizontal margin */ + + hmargin = gw->label.internal_width ; + vmargin = gw->label.internal_height ; + + /* find total height (width) of contents */ + + + /* find minimum size for undecorated gauge */ + + if( gw->gauge.orientation == XtorientHorizontal ) + { + w = min_len ; + h = GA_WID+2 ; /* gauge itself + edges */ + } + else + { + w = GA_WID+2 ; + h = min_len ; + } + + if( gw->gauge.ntics > 0 ) + { + if( gw->gauge.orientation == XtorientHorizontal ) + { + w = Max(w, gw->gauge.ntics*3) ; + h += vmargin + TIC_LEN ; + } + else + { + w += hmargin + TIC_LEN ; + h = Max(h, gw->gauge.ntics*3) ; + } + } + + + /* If labels are requested, this gets a little interesting. + * We want the end labels centered on the ends of the gauge and + * the centers of the labels evenly spaced. The labels at the ends + * will not be the same width, meaning that the gauge itself need + * not be centered in the widget. + * + * First, determine the spacing. This is the width of the widest + * label, plus the internal margin. Total length of the gauge is + * spacing * (nlabels-1). To this, we add half the width of the + * left-most label and half the width of the right-most label + * to get the entire desired width of the widget. + */ + if( gw->gauge.nlabels > 0 ) + { + Dimension lwm, lw0, lw1 ; /* width of max, left, right labels */ + Dimension lh ; + + MaxLabel(gw,&lwm,&lh, &lw0,&lw1) ; + + if( gw->gauge.orientation == XtorientHorizontal ) + { + lwm = (lwm+hmargin) * (gw->gauge.nlabels-1) + (lw0+lw1)/2 ; + w = Max(w, lwm) ; + h += lh + vmargin ; + } + else + { + lh = lh*gw->gauge.nlabels + (gw->gauge.nlabels - 1)*vmargin ; + h = Max(h, lh) ; + w += lwm + hmargin ; + } + } + + w += hmargin*2 ; + h += vmargin*2 ; + + *wid = w ; + *hgt = h ; +} + + + +static void +AutoScale (GaugeWidget gw) +{ + static int scales[3] = {1,2,5} ; + int sptr = 0, smult=1 ; + + if( gw->gauge.autoScaleDown ) + gw->gauge.v1 = 0 ; + while( gw->gauge.value > gw->gauge.v1 ) + { + if( ++sptr > 2 ) { + sptr = 0 ; + smult *= 10 ; + } + gw->gauge.v1 = scales[sptr] * smult ; + } +} + +static void +EnableUpdate (GaugeWidget gw) +{ + gw->gauge.intervalId = + XtAppAddTimeOut(XtWidgetToApplicationContext((Widget)gw), + gw->gauge.update * MS_PER_SEC, GaugeGetValue, + (XtPointer)gw) ; +} + +static void +DisableUpdate (GaugeWidget gw) +{ + XtRemoveTimeOut(gw->gauge.intervalId) ; +} + +static void +GaugeGetValue (XtPointer clientData, + XtIntervalId *intervalId) +{ + GaugeWidget gw = (GaugeWidget)clientData ; + Cardinal value ; + + if( gw->gauge.update > 0 ) + EnableUpdate(gw) ; + + if( gw->gauge.getValue != NULL ) + { + XtCallCallbackList((Widget)gw, gw->gauge.getValue, (XtPointer)&value); + XawGaugeSetValue((Widget)gw, value) ; + } +} + + +static GC +Get_GC (GaugeWidget gw, + Pixel fg) +{ + XGCValues values ; +#define vmask GCForeground +#define umask (GCBackground|GCSubwindowMode|GCGraphicsExposures|GCDashOffset\ + |GCFont|GCDashList|GCArcMode) + + values.foreground = fg ; + + return XtAllocateGC((Widget)gw, 0, vmask, &values, 0L, umask) ; +} diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwgauge.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwgauge.h Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,184 @@ +/* Gauge Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* Synched up with: Gauge.h 1.1 */ + +/* + * Gauge.h - Gauge widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: July 8, 1997 + */ + +#ifndef _XawGauge_h +#define _XawGauge_h + +/*********************************************************************** + * + * Gauge Widget + * + * The Gauge widget looks something like a thermometer. Application + * defines the values at the ends of the range and the current value + * and Gauge draws accordingly. Gauge does not accept input. + * + ***********************************************************************/ + +#include + +/* Resources: + + Name Class RepType Default Value + ---- ----- ------- ------------- + value Value Cardinal 0 + minValue MinValue Cardinal 0 + maxValue MaxValue Cardinal 100 + ntics NTics Cardinal 0 + + nlabels NLabels Cardinal 0 ++ + labels Labels String * NULL +++ + orientation Orientation XtOrientation horizontal + autoScaleUp AutoScaleUp Boolean FALSE ++++ + autoScaleDown AutoScaleDown Boolean FALSE ++++ + getValue Callback XtCallbackList NULL +++++ + update Interval int 0 (seconds) = disabled + + encoding Encoding unsigned char XawTextEncoding8bit + font Font XFontStruct* XtDefaultFont + foreground Foreground Pixel XtDefaultForeground + internalHeight Height Dimension 2 + internalWidth Width Dimension 4 + resize Resize Boolean True + background Background Pixel XtDefaultBackground + bitmap Pixmap Pixmap None + border BorderColor Pixel XtDefaultForeground + borderWidth BorderWidth Dimension 1 + cursor Cursor Cursor None + cursorName Cursor String NULL + destroyCallback Callback XtCallbackList NULL + height Height Dimension varies + insensitiveBorder Insensitive Pixmap Gray + mappedWhenManaged MappedWhenManaged Boolean True + pointerColor Foreground Pixel XtDefaultForeground + pointerColorBackground Background Pixel XtDefaultBackground + sensitive Sensitive Boolean True + width Width Dimension text width + x Position Position 0 + y Position Position 0 + + + Ntics sets the number of tic marks next to the gauge. If 0, no + tic marks will be drawn. + ++ Nlabels sets the number of labels next to the gauge. + +++ Labels is an array of nul-terminated strings to be used as labels. + If this field is NULL but nlabels is > 0, then numeric labels will be + provided. NOTE: the labels are not copied to any internal memory; they + must be stored in static memory provided by the appliction. + ++++ AutoScale allows the gauge to set its own value limits. Default is + False unless upper & lower limits are both 0. + + +++++ The GetValue() callback proc is called with these arguments: + static void + myGetValue(gauge, client, rval) + Widget gauge ; + XtPointer client ; + XtPointer rval ; + { + *(Cardinal *)rval = value ; + } + +*/ + +/* + * Resource names not provided in StringDefs.h + */ + +#ifndef XtNvalue +#define XtNvalue "value" +#define XtCValue "Value" +#endif + +#ifndef XtNorientation +#define XtNorientation "orientation" +#define XtCOrientation "Orientation" +#endif + +#define XtNntics "ntics" +#define XtCNTics "NTics" + +#ifndef XtNnlabels +#define XtNnlabels "nlabels" +#define XtCNLabels "NLabels" +#endif +#ifndef XtNlabels +#define XtNlabels "labels" +#define XtCLabels "Labels" +#endif + +#ifndef XtNminValue +#define XtNminValue "minValue" +#define XtCMinValue "MinValue" +#endif +#ifndef XtNmaxValue +#define XtNmaxValue "maxValue" +#define XtCMaxValue "MaxValue" +#endif + +#ifndef XtNautoScaleUp +#define XtNautoScaleUp "autoScaleUp" +#define XtCAutoScaleUp "AutoScaleUp" +#define XtNautoScaleDown "autoScaleDown" +#define XtCAutoScaleDown "AutoScaleDown" +#endif + +#ifndef XtNupdate +#define XtNupdate "update" +#endif + +#ifndef XtNgetValue +#define XtNgetValue "getValue" +#endif + + +/* Class record constants */ + +extern WidgetClass gaugeWidgetClass; + +typedef struct _GaugeClassRec *GaugeWidgetClass; +typedef struct _GaugeRec *GaugeWidget; + + +_XFUNCPROTOBEGIN + +extern void XawGaugeSetValue( +#if NeedFunctionPrototypes + Widget gauge, + Cardinal value +#endif +); + +extern Cardinal XawGaugeGetValue( +#if NeedFunctionPrototypes + Widget gauge +#endif +); + +_XFUNCPROTOEND + +#endif /* _XawGauge_h */ diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwgaugeP.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwgaugeP.h Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,103 @@ +/* Gauge Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* + * GaugeP.h - Gauge widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: July 9, 1997 + */ + +#ifndef _XawGaugeP_h +#define _XawGaugeP_h + +/*********************************************************************** + * + * Gauge Widget Private Data + * + * Gauge has little in common with the label widget, but can make use + * of some label resources, so is subclassed from label. + * + ***********************************************************************/ + +#include "xlwgauge.h" +#include + +/* New fields for the Gauge widget class record */ + +typedef struct {XtPointer extension;} GaugeClassPart; + +/* Full class record declaration */ +typedef struct _GaugeClassRec { + CoreClassPart core_class; + SimpleClassPart simple_class; +#ifdef _ThreeDP_h + ThreeDClassPart threeD_class; +#endif + LabelClassPart label_class; + GaugeClassPart gauge_class; +} GaugeClassRec; + +extern GaugeClassRec gaugeClassRec; + +/* New fields for the Gauge widget record */ +typedef struct { + /* resources */ + int value, v0,v1 ; + int ntics, nlabels ; + String *labels ; + XtOrientation orientation ; + Boolean autoScaleUp ; /* scales automatically */ + Boolean autoScaleDown ; /* scales automatically */ + int update ; /* update interval */ + XtCallbackList getValue ; /* proc to call to fetch a point */ + + /* private state */ + Dimension gmargin ; /* edges <-> gauge */ + Dimension tmargin ; /* top (left) edge <-> tic marks */ + Dimension lmargin ; /* tic marks <-> labels */ + Dimension margin0 ; /* left/bottom margin */ + Dimension margin1 ; /* right/top margin */ + XtIntervalId intervalId ; + Atom selected ; + String selstr ; /* selection string, if any */ + GC inverse_GC ; +} GaugePart; + + +/**************************************************************** + * + * Full instance record declaration + * + ****************************************************************/ + +typedef struct _GaugeRec { + CorePart core; + SimplePart simple; +#ifdef _ThreeDP_h + ThreeDPart threeD; +#endif + LabelPart label; + GaugePart gauge; +} GaugeRec; + +#endif /* _XawGaugeP_h */ diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwgcs.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwgcs.c Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,545 @@ + /* Tabs Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + + This file is part of XEmacs. + + XEmacs is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 2, or (at your option) any + later version. + + XEmacs is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with XEmacs; see the file COPYING. If not, write to + the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + +/* Synched up with: Gcs.c 1.7 */ + + /* #### This code is duplicated many times within lwlib and XEmacs. It + should be modularised. */ + +/* + * Gcs.c - Utility functions to allocate GCs. + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: Sept 29, 1998 + */ + +/* Functions: + * + * GC AllocFgGC(w, fg, font) + * Return a GC with foreground set as specified. + * If font is None, then the returned GC is allocated with font specified + * as a "don't care" value. + * + * GC + * AllocBackgroundGC(w, font) + * Return a GC with the foreground set to the widget's background color. + * + * GC + * AllocGreyGC(w, fg, font, contrast, be_nice_to_cmap) + * Widget w ; + * Pixel fg ; + * Font font ; + * int contrast ; + * int be_nice_to_cmap ; + * + * Return a GC suitable for rendering a widget in its "inactive" color. + * Normally returns a GC with a color somewhere between the widget's + * background color and the specified foreground. If font is None, then + * the returned GC is allocated with font specified as "don't care". + * If be_nice_to_cmap is True, the returned GC is created using a 50% + * dither instead of a new color. + * + * + * GC + * AllocShadeGC(w, fg, bg, font, contrast, be_nice_to_cmap) + * Widget w ; + * Pixel fg, bg ; + * Font font ; + * int contrast ; + * int be_nice_to_cmap ; + * + * Return a GC suitable for rendering in a shade somewhere between + * bg and fg, as determined by contrast (0 = bg, 100 = fg) + * If font is None, then the returned GC is allocated with + * font specified as "don't care". If be_nice_to_cmap + * is True, the returned GC is created using a 50% dither + * instead of a new color. + * + * + * GC + * AllocTopShadowGC(w, contrast, be_nice_to_cmap) + * Return a GC suitable for rendering the "top shadow" decorations of + * a widget. Returns a GC with foreground computed from widget's + * background color and contrast. If be_nice_to_cmap is True, the + * returned GC will use a foreground color of white. If widget depth + * is 1, this function will use a foreground color of black. + * + * GC + * AllocBotShadowGC(w, contrast, be_nice_to_cmap) + * Return a GC suitable for rendering the "bottom shadow" decorations + * of a widget. Returns a GC with foreground computed from widget's + * background color and contrast. If be_nice_to_cmap is True, the + * returned GC will use a foreground color of black. + * + * GC + * AllocArmGC(w, contrast, be_nice_to_cmap) + * Return a GC suitable for rendering the "armed" decorations of a + * widget. This GC would typically be used to fill in the widget's + * background. Returns a GC with foreground computed from widget's + * background color and contrast. If be_nice_to_cmap is True, the + * returned GC will use a foreground color of black and a 50% dither. + * + * + * void + * Draw3dBox(w, x,y,wid,hgt,s, topgc, botgc) + * Utility function. Draws a raised shadow box with outside dimensions + * as specified by x,y,wid,hgt and shadow width specified by s. + * A lowered shadow box may be generated by swapping topgc and botgc. + * + */ + +#include +#include + +#include +#include +#include +#include "../src/xmu.h" +#include "xlwgcs.h" + + /* Color & GC allocation. + * + * Frame widgets use the following graphics contexts: + * + * Foreground tab label text drawn this way + * Insensitive Fg foreground color greyed out. + * Background frame background color + * Top shadow upper-left highlight around widget + * Bottom shadow lower-right highlight around widget + * Arm shadow button pressed and ready to be released + * + * + * GC's are defined as follows, depending on attributes and + * window depth: + * + * Monochrome: + * Foreground = foreground color attribute or BlackPixel() + * Grey = Foreground color + 50% dither + * Background = background color attribute or WhitePixel() + * top shadow = foreground + * bottom shadow = foreground + * arm shadow = (what?) + * + * Color, beNiceToColormap=true: + * Foreground = foreground color attribute or BlackPixel() + * Grey = Foreground color + 50% dither + * Background = background color attribute or WhitePixel() + * top shadow = white + * bottom shadow = black + * arm shadow = (what?) + * + * Color, beNiceToColormap=false: + * Foreground = foreground color attribute or BlackPixel() + * Grey = (foreground color + background color)/2 + * Background = background color attribute or WhitePixel() + * top shadow = background * 1.2 + * bottom shadow = background * .6 + * arm shadow = background * .8 + * + * Special cases: + * If background is white, ?? + * if background is black, ?? + * + * + * If the widget's background is solid white or solid black, + * this code just picks some numbers. (The choice is designed + * to be compatibile with ThreeD interface.) + */ + + + +#if XtSpecificationRelease < 5 + +static GC XtAllocateGC(Widget, int, u_long, XGCValues *, u_long, u_long) ; + +#endif + + +#if NeedFunctionPrototypes +static Pixmap getDitherPixmap(Widget, int contrast) ; +#else +static Pixmap getDitherPixmap() ; +#endif + + /* return a GC with the specified foreground and optional font */ + +GC +AllocFgGC(Widget w, Pixel fg, Font font) +{ + XGCValues values ; + u_long vmask, dcmask ; + + values.foreground = fg ; + values.font = font ; + + if( font != None ) { + vmask = GCForeground|GCFont ; + dcmask = GCSubwindowMode|GCDashOffset| + GCDashList|GCArcMode|GCBackground|GCGraphicsExposures ; + } else { + vmask = GCForeground ; + dcmask = GCFont|GCSubwindowMode|GCDashOffset| + GCDashList|GCArcMode|GCBackground|GCGraphicsExposures ; + } + + return XtAllocateGC(w, w->core.depth, vmask, &values, 0L, dcmask) ; +} + + + /* return gc with widget background color as the foreground */ + +GC +AllocBackgroundGC(Widget w, Font font) +{ + return AllocFgGC(w, w->core.background_pixel, font) ; +} + + + /* Allocate an "inactive" GC. Color is grey (possibly via + * dither pattern). + */ + +GC +AllocGreyGC(Widget w, Pixel fg, Font font, int contrast, Bool be_nice_to_cmap) +{ + return AllocShadeGC(w, fg, w->core.background_pixel, + font, contrast, be_nice_to_cmap) ; +} + + + /* Allocate a GC somewhere between two colors. */ + +GC +AllocShadeGC(Widget w, Pixel fg, Pixel bg, Font font, + int contrast, Bool be_nice_to_cmap) +{ + XGCValues values ; + u_long vmask, dcmask ; + + values.foreground = fg ; + values.background = bg ; + values.font = font ; + + if( font != None ) { + vmask = GCForeground|GCFont ; + dcmask = GCSubwindowMode|GCDashOffset| + GCDashList|GCArcMode|GCGraphicsExposures ; + } else { + vmask = GCForeground; + dcmask = GCFont|GCSubwindowMode|GCDashOffset| + GCDashList|GCArcMode|GCGraphicsExposures ; + } +#ifdef HAVE_XMU + if( be_nice_to_cmap || w->core.depth == 1) + { + if( contrast <= 5 ) + values.foreground = bg ; + else if( contrast >= 95 ) + values.foreground = fg ; + else { + vmask |= GCBackground|GCStipple|GCFillStyle ; + values.fill_style = FillOpaqueStippled ; + values.stipple = getDitherPixmap(w, contrast) ; + } + + return XtAllocateGC(w, w->core.depth, vmask, &values, 0L, dcmask) ; + } + else +#endif + { + dcmask |= GCBackground ; + values.foreground = AllocGreyPixel(w, fg, bg, contrast) ; + return XtAllocateGC(w, w->core.depth, vmask, &values, 0L, dcmask) ; + } +} + + /* return top-shadow gc. */ + +GC +AllocTopShadowGC(Widget w, int contrast, Bool be_nice_to_cmap) +{ + Screen *scr = XtScreen (w); + XGCValues values ; + + if( w->core.depth == 1 ) + values.foreground = BlackPixelOfScreen(scr) ; + else if( be_nice_to_cmap ) + values.foreground = WhitePixelOfScreen(scr) ; + else + values.foreground = AllocShadowPixel(w, 100+contrast) ; + + return XtAllocateGC(w, w->core.depth, + GCForeground, &values, + 0L, + GCBackground|GCFont|GCSubwindowMode|GCGraphicsExposures| + GCDashOffset|GCDashList|GCArcMode) ; +} + + /* return bottom-shadow gc. */ + +GC +AllocBotShadowGC(Widget w, int contrast, Bool be_nice_to_cmap) +{ + Screen *scr = XtScreen (w); + XGCValues values ; + + if( w->core.depth == 1 || be_nice_to_cmap ) + values.foreground = BlackPixelOfScreen(scr) ; + else + values.foreground = AllocShadowPixel(w, 100-contrast) ; + + return XtAllocateGC(w, w->core.depth, + GCForeground, &values, + 0L, + GCBackground|GCFont|GCSubwindowMode|GCGraphicsExposures| + GCDashOffset|GCDashList|GCArcMode) ; +} + + /* return arm-shadow gc. */ + +GC +AllocArmGC(Widget w, int contrast, Bool be_nice_to_cmap) +{ + Screen *scr = XtScreen (w); + XGCValues values ; + + /* Not clear exactly what we should do here. Take a look at + * Xaw3d to see what they do. + */ +#ifdef HAVE_XMU + if( w->core.depth == 1 || be_nice_to_cmap ) + { + values.background = w->core.background_pixel ; + if( values.background == BlackPixelOfScreen(scr) ) + values.foreground = WhitePixelOfScreen(scr) ; + else + values.foreground = BlackPixelOfScreen(scr) ; + values.fill_style = FillStippled ; + values.stipple = XmuCreateStippledPixmap(XtScreen(w), 1L, 0L, 1) ; + + return XtAllocateGC(w, w->core.depth, + GCForeground|GCBackground|GCStipple|GCFillStyle, + &values, 0L, + GCFont|GCSubwindowMode|GCGraphicsExposures| + GCDashOffset|GCDashList|GCArcMode) ; + } + else +#endif + { + values.foreground = AllocShadowPixel(w, 100-contrast) ; + return XtAllocateGC(w, w->core.depth, + GCForeground, &values, + 0L, + GCBackground|GCFont|GCSubwindowMode|GCGraphicsExposures| + GCDashOffset|GCDashList|GCArcMode) ; + } +} + + +Pixel +AllocShadowPixel(Widget w, int scale) +{ + XColor get_c, set_c ; + Display *dpy = XtDisplay(w) ; + Screen *scr = XtScreen(w) ; + Colormap cmap ; + Pixel maxColor ; + + cmap = w->core.colormap ; + + get_c.pixel = w->core.background_pixel ; + if( get_c.pixel == WhitePixelOfScreen(scr) || + get_c.pixel == BlackPixelOfScreen(scr) ) + { + /* what we *ought* to do is choose gray75 as the base color, + * or perhaps gray83. Instead, we choose colors that are + * the same as ThreeD would choose. + */ + if( scale > 100 ) scale = 200 - scale ; + set_c.red = set_c.green = set_c.blue = 65535*scale/100 ; + } + else + { + XQueryColor(dpy, cmap, &get_c) ; + /* adjust scale so that brightest component does not + * exceed 65535; otherwise hue would change. + */ + if( scale > 100 ) { + maxColor = Max(get_c.red, Max(get_c.green, get_c.blue)) ; + if( scale*maxColor > 65535*100 ) + scale = 65535*100/maxColor ; + } + set_c.red = scale * get_c.red / 100 ; + set_c.green = scale * get_c.green / 100 ; + set_c.blue = scale * get_c.blue / 100 ; + } + set_c.flags = DoRed | DoGreen | DoBlue ; + if( XAllocColor(dpy, cmap, &set_c) ) + return set_c.pixel ; + else if( scale > 100 ) + return WhitePixelOfScreen(scr) ; + else + return BlackPixelOfScreen(scr) ; +} + + + /* Allocate a pixel partway between foreground and background */ + + +Pixel +AllocGreyPixel(Widget w, Pixel fg, Pixel bg, int scale) +{ + XColor get_cf, get_cb ; + Display *dpy = XtDisplay(w) ; + Colormap cmap ; + + cmap = w->core.colormap ; + + get_cf.pixel = fg ; + get_cb.pixel = bg ; + + XQueryColor(dpy, cmap, &get_cf) ; + XQueryColor(dpy, cmap, &get_cb) ; + + return AllocGreyPixelC(w, &get_cf, &get_cb, scale) ; +} + + + + /* Allocate a pixel partway between foreground and background */ + + +Pixel +AllocGreyPixelC(Widget w, XColor *fg, XColor *bg, int scale) +{ + XColor set_c ; + Display *dpy = XtDisplay(w) ; + int r,g,b ; + Colormap cmap = w->core.colormap ; + + r = (fg->red * scale + bg->red * (100-scale)) / 100 ; + g = (fg->green * scale + bg->green * (100-scale)) / 100 ; + b = (fg->blue * scale + bg->blue * (100-scale)) / 100 ; + + if( scale > 100 || scale < 0 ) /* look out for overflow */ + { + int minc, maxc ; + maxc = Max(r, Max(g,b)) ; + minc = Min(r, Min(g,b)) ; + if( maxc > 65535 ) + { + maxc /= 16 ; + r = r*(65535/16) / maxc ; + g = g*(65535/16) / maxc ; + b = b*(65535/16) / maxc ; + } + if( minc < 0 ) + { + r = Max(r,0) ; + g = Max(g,0) ; + b = Max(b,0) ; + } + } + + set_c.red = r ; set_c.green = g ; set_c.blue = b ; + set_c.flags = DoRed | DoGreen | DoBlue ; + (void)XAllocColor(dpy, cmap, &set_c) ; + return set_c.pixel ; +} + + + + + + /* draw a 3-d box */ + +void +Draw3dBox(Widget w, int x, int y, int wid, int hgt, int s, GC topgc, GC botgc) +{ + Display *dpy = XtDisplay(w) ; + Window win = XtWindow(w) ; + + if( s == 0 ) return ; + + if( s == 1 ) { + XDrawLine(dpy,win,botgc, x,y+hgt-1, x+wid-1,y+hgt-1) ; + XDrawLine(dpy,win,botgc, x+wid-1,y, x+wid-1,y+hgt-1) ; + XDrawLine(dpy,win,topgc, x,y, x,y+hgt-1) ; + XDrawLine(dpy,win,topgc, x,y, x+wid-1,y) ; + } + else + { + XPoint pts[6] ; + + /* bottom-right shadow */ + pts[0].x = x ; pts[0].y = y + hgt ; + pts[1].x = s ; pts[1].y = -s ; + pts[2].x = wid-2*s ; pts[2].y = 0 ; + pts[3].x = 0 ; pts[3].y = -(hgt-2*s) ; + pts[4].x = s ; pts[4].y = -s ; + pts[5].x = 0 ; pts[5].y = hgt ; + XFillPolygon(dpy,win,botgc, pts,6, Nonconvex,CoordModePrevious) ; + + /* top-left shadow */ + pts[0].x = x ; pts[0].y = y ; + pts[1].x = wid ; pts[1].y = 0 ; + pts[2].x = -s ; pts[2].y = s ; + pts[3].x = -wid+2*s ; pts[3].y = 0 ; + pts[4].x = 0 ; pts[4].y = hgt-2*s ; + pts[5].x = -s ; pts[5].y = s ; + XFillPolygon(dpy,win,topgc, pts,6, Nonconvex,CoordModePrevious) ; + } +} + +#if XtSpecificationRelease < 5 + +static GC +XtAllocateGC(Widget w, int depth, u_long mask, XGCValues *values, + u_long dynamic, du_long ontcare) +{ + return XtGetGC(w, mask, values) ; +} +#endif + + +static u_char screen0[2] = {0,0} ; +static u_char screen25[2] = {0,0xaa} ; +static u_char screen75[2] = {0xaa,0xff} ; +static u_char screen100[2] = {0xff,0xff} ; + +static Pixmap +getDitherPixmap(Widget w, int contrast) +{ + Display *dpy = XtDisplay(w) ; + Window win = XtWindow(w) ; + + if( contrast <= 5 ) + return XCreateBitmapFromData(dpy,win, (char *)screen0, 2,2) ; + else if( contrast <= 37 ) + return XCreateBitmapFromData(dpy,win, (char *)screen25, 2,2) ; + else if( contrast <= 62 ) + return XmuCreateStippledPixmap(XtScreen(w), 1L, 0L, 1) ; + else if( contrast <= 95 ) + return XCreateBitmapFromData(dpy,win, (char *)screen75, 2,2) ; + else + return XCreateBitmapFromData(dpy,win, (char *)screen100, 2,2) ; +} diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwgcs.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwgcs.h Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,144 @@ + /* Tabs Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + + This file is part of XEmacs. + + XEmacs is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 2, or (at your option) any + later version. + + XEmacs is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with XEmacs; see the file COPYING. If not, write to + the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + + /* Synched up with: Gcs 1.7 */ + + +#ifndef GCS_H +#define GCS_H + +/* Overview of functions provided here: + * + * AllocFgGC() + * Given a foreground pixel & a font, return an appropriate GC + * + * AllocBackgroundGC() + * Given a widget, return a GC for painting the background color + * + * AllocShadeGC() + * Given foreground, background, a contrast value & be_nice_to_colormap + * flag, return a GC suitable for rendering in an intermediate color, + * as determined by constrast. May return a dither pattern or a + * solid color, as appropriate. + * + * Contrast 0 = background color, 100 = foreground color. It is legal + * for contrast to be more than 100 or less than 0. + * + * AllocGreyGC() + * Given widget, foreground, font, contrast & be_nice_to_colormap, + * return a shade GC (see above) based on foreground and widget + * background. + * + * AllocTopShadowGC() + * Given widget, contrast & be_nice_to_colormap, return a GC suitable + * for rendering the top shadow. + * + * Contrast 0 = use background pixel. Contrast > 0 = use brighter + * colors. + * + * AllocBotShadowGC() + * Given widget, contrast & be_nice_to_colormap, return a GC suitable + * for rendering the bottom shadow. + * + * Contrast 0 = use background pixel. Contrast > 0 = use darker + * colors. + * + * AllocArmShadowGC() + * Given widget, contrast & be_nice_to_colormap, return a GC suitable + * for rendering the "armed" shadow. + * + * Contrast 0 = use background pixel. Contrast > 0 = use darker + * colors. + * + * AllocShadowPixel() + * Given a widget & scale factor, allocate & return a color darker + * or lighter than the background pixel, as determined by scale. + * + * Scale 100 = use background pixel. Scale > 100 = brighter color, + * Scale < 100 = darker color. + * + * AllocGreyPixel() + * Given two pixel values and scale factor, allocate & return a + * pixel value between them, according to scale. + * + * Scale == 0: background color + * Scale == 100: foreground color + * 0 100: more foreground + * Scale < 0: more background + * + * + * AllocGreyPixelC() + * Given two color values and scale factor, allocate & return a + * pixel value between them, according to scale. + * + * Scale == 0: background color + * Scale == 100: foreground color + * 0 100: more foreground + * Scale < 0: more background + * + * Draw3dBox() + * Given box dimensions, shadow width, top shadow GC & bottom shadow GC, + * draw a 3-d box. + */ + +#if NeedFunctionPrototypes + +extern GC AllocFgGC( Widget w, Pixel fg, Font font) ; +extern GC AllocBackgroundGC( Widget w, Font font) ; +extern GC AllocShadeGC( Widget w, Pixel fg, Pixel bg, Font, + int contrast, Bool ) ; +extern GC AllocGreyGC( Widget w, Pixel fg, Font, int, Bool ) ; +extern GC AllocTopShadowGC( Widget w, int contrast, int ) ; +extern GC AllocBotShadowGC( Widget w, int contrast, int ) ; +extern GC AllocArmGC( Widget w, int contrast, int) ; +extern Pixel AllocShadowPixel(Widget, int scale) ; +extern Pixel AllocGreyPixel(Widget, Pixel fg, Pixel bg, int scale) ; +extern Pixel AllocGreyPixelC(Widget, XColor *fg, XColor *bg, int scale) ; +extern void Draw3dBox(Widget w, int x, int y, int wid, int hgt, int s, + GC topgc, GC botgc) ; + +#if XtSpecificationRelease < 5 +extern GC XtAllocateGC(Widget, int depth, u_long mask, + XGCValues *, u_long dynamic, u_long dontcare) ; +#endif + +#else + +extern GC AllocFgGC() ; +extern GC AllocBackgroundGC() ; +extern GC AllocShadeGC() ; +extern GC AllocGreyGC() ; +extern GC AllocTopShadowGC() ; +extern GC AllocBotShadowGC() ; +extern GC AllocArmGC() ; +extern Pixel AllocShadowPixel() ; +extern Pixel AllocGreyPixel() ; +extern Pixel AllocGreyPixelC() ; +extern void Draw3dBox() ; + +#if XtSpecificationRelease < 5 +extern GC XtAllocateGC() ; +#endif + +#endif + +#endif /* GCS_H */ diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwradio.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwradio.c Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,590 @@ +/* Radio Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* Synched up with: Radio.c 1.1 */ + +/* + * Radio.c - Radio button widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: June 30, 1997 + * + * + * Overview: This widget is identical to the Toggle widget in behavior, + * but completely different in appearance. This widget looks like a small + * diamond-shaped button with a label to the right. + * + * To make this work, we subclass the Toggle widget to inherit its behavior + * and to inherit the label-drawing function from which Toggle is + * subclassed. We then completely replace the Expose, Set, Unset + * and Highlight member functions. + * + * The Set and Unset actions are slightly unorthodox. In Toggle's + * ClassInit function, Toggle searches the Command actions list and + * "steals" the Set and Unset functions, caching pointers to them in its + * class record. It then calls these functions from its own ToggleSet + * and Toggle actions. + * + * We, in turn, override the Set() and Unset() actions in our own ClassRec. + */ + + +#include +#include + +#include +#include +#include +#include "../src/xmu.h" +#include "xlwradioP.h" + +#define BOX_SIZE 13 + +#define rclass(w) ((RadioWidgetClass)((w)->core.widget_class)) + + +#ifdef _ThreeDP_h +#define swid(rw) ((rw)->threeD.shadow_width) +#else +#define swid(rw) ((rw)->core.border_width) +#endif + +#define bsize(rw) (rclass(rw)->radio_class.dsize) +#define bs(rw) (bsize(rw) + 2*swid(rw)) + + + +/**************************************************************** + * + * Full class record constant + * + ****************************************************************/ + + /* The translations table from Toggle do not need to be + * overridden by Radio + */ + + + /* Member functions */ + +static void RadioInit (Widget, Widget, ArgList, Cardinal *); +static void RadioExpose (Widget, XEvent *, Region); +static void RadioResize (Widget); +static void RadioDestroy (Widget, XtPointer, XtPointer); +static void RadioClassInit (void); +static void RadioClassPartInit (WidgetClass); +static Boolean RadioSetValues (Widget, Widget, Widget, ArgList, Cardinal *); +static void DrawDiamond (Widget); +static XtGeometryResult RadioQueryGeometry (Widget, XtWidgetGeometry *, + XtWidgetGeometry *); + + /* Action procs */ + +static void RadioHighlight (Widget, XEvent *, String *, Cardinal *); +static void RadioUnhighlight (Widget, XEvent *, String *, Cardinal *); + + /* internal privates */ + +static void RadioSize (RadioWidget, Dimension *, Dimension *); + + /* The actions table from Toggle is almost perfect, but we need + * to override Highlight, Set, and Unset. + */ + +static XtActionsRec actionsList[] = +{ + {"highlight", RadioHighlight}, + {"unhighlight", RadioUnhighlight}, +}; + +#define SuperClass ((ToggleWidgetClass)&toggleClassRec) + +RadioClassRec radioClassRec = { + { + (WidgetClass) SuperClass, /* superclass */ + "Radio", /* class_name */ + sizeof(RadioRec), /* size */ + RadioClassInit, /* class_initialize */ + RadioClassPartInit, /* class_part_initialize */ + FALSE, /* class_inited */ + RadioInit, /* initialize */ + NULL, /* initialize_hook */ + XtInheritRealize, /* realize */ + actionsList, /* actions */ + XtNumber(actionsList), /* num_actions */ + NULL, /* resources */ + 0, /* resource_count */ + NULLQUARK, /* xrm_class */ + TRUE, /* compress_motion */ + TRUE, /* compress_exposure */ + TRUE, /* compress_enterleave */ + FALSE, /* visible_interest */ + NULL, /* destroy */ + RadioResize, /* resize */ + RadioExpose, /* expose */ + RadioSetValues, /* set_values */ + NULL, /* set_values_hook */ + XtInheritSetValuesAlmost, /* set_values_almost */ + NULL, /* get_values_hook */ + NULL, /* accept_focus */ + XtVersion, /* version */ + NULL, /* callback_private */ + XtInheritTranslations, /* tm_table */ + RadioQueryGeometry, /* query_geometry */ + XtInheritDisplayAccelerator, /* display_accelerator */ + NULL /* extension */ + }, /* CoreClass fields initialization */ + { + XtInheritChangeSensitive /* change_sensitive */ + }, /* SimpleClass fields initialization */ +#ifdef _ThreeDP_h + { + XtInheritXaw3dShadowDraw /* field not used */ + }, /* ThreeDClass fields initialization */ +#endif + { + 0 /* field not used */ + }, /* LabelClass fields initialization */ + { + 0 /* field not used */ + }, /* CommandClass fields initialization */ + { + RadioSet, /* Set Procedure. */ + RadioUnset, /* Unset Procedure. */ + NULL /* extension. */ + }, /* ToggleClass fields initialization */ + { + BOX_SIZE, + DrawDiamond, /* draw procedure */ + NULL /* extension. */ + } /* RadioClass fields initialization */ +}; + + /* for public consumption */ +WidgetClass radioWidgetClass = (WidgetClass) &radioClassRec; + + + + + + +/**************************************************************** + * + * Class Methods + * + ****************************************************************/ + +static void +RadioClassInit (void) +{ + XawInitializeWidgetSet(); +} + +static void +RadioClassPartInit (WidgetClass class) +{ + RadioWidgetClass c = (RadioWidgetClass) class ; + RadioWidgetClass super = (RadioWidgetClass)c->core_class.superclass ; + + if( c->radio_class.drawDiamond == NULL || + c->radio_class.drawDiamond == XtInheritDrawDiamond ) + { + c->radio_class.drawDiamond = super->radio_class.drawDiamond ; + } +} + + + + +/*ARGSUSED*/ +static void +RadioInit (Widget request, + Widget new, + ArgList args, + Cardinal *num_args) +{ + RadioWidget rw = (RadioWidget) new; + RadioWidget rw_req = (RadioWidget) request; + Dimension w,h ; + + /* Select initial size for the widget */ + if( rw_req->core.width == 0 || rw_req->core.height == 0 ) + { + RadioSize(rw, &w,&h) ; + if( rw_req->core.width == 0 ) + rw->core.width = w ; + if( rw_req->core.height == 0 ) + rw->core.height = h ; + rw->core.widget_class->core_class.resize(new) ; + } +} + +/* Function Name: RadioDestroy + * Description: Destroy Callback for radio widget. + * Arguments: w - the radio widget that is being destroyed. + * junk, grabage - not used. + * Returns: none. + */ + +/* ARGSUSED */ +static void +RadioDestroy (Widget w, + XtPointer junk, + XtPointer garbage) +{ + /* TODO: get rid of this */ +} + + +/* React to size change from manager. Label widget will compute some internal + * stuff, but we need to override. This code requires knowledge of the + * internals of the Label widget. + */ + +static void +RadioResize (Widget w) +{ + RadioWidget rw = (RadioWidget)w ; + + /* call parent resize proc */ + SuperClass->core_class.resize(w) ; + + /* override label offset */ + + switch( rw->label.justify ) { + case XtJustifyLeft: + rw->label.label_x += bs(rw) + rw->label.internal_width ; + break ; + case XtJustifyRight: + break ; + case XtJustifyCenter: + default: + rw->label.label_x += (bs(rw) + rw->label.internal_width)/2 ; + break ; + } +} + + +/* + * Repaint the widget window. + */ + +static void +RadioExpose (Widget w, + XEvent *event, + Region region) +{ + RadioWidget rw = (RadioWidget) w ; + Display *dpy = XtDisplay(w) ; + Window win = XtWindow(w) ; + GC gc ; + Pixmap left_bitmap ; + extern WidgetClass labelWidgetClass ; + + /* Note: the Label widget examines the region to decide if anything + * needs to be drawn. I'm not sure that this is worth the effort, + * but it bears thinking on. + */ + + /* Command widget may sometimes override the label GC in order + * to draw inverse video. We don't use inverse video, so we need + * to restore the label's normal GC. + */ + rw->label.normal_GC = rw->command.normal_GC ; + + + /* Let label widget draw the label. If there was an lbm_x + * field, we could let Label draw the bitmap too. But there + * isn't, so we need to temporarily remove the bitmap and + * draw it ourself later. + */ + left_bitmap = rw->label.left_bitmap ; + rw->label.left_bitmap = None ; + labelWidgetClass->core_class.expose(w,event,region) ; + rw->label.left_bitmap = left_bitmap ; + + /* now manually draw the left bitmap. TODO: 3-d look, xaw-xpm */ + gc = XtIsSensitive(w) ? rw->label.normal_GC : rw->label.gray_GC ; + if( left_bitmap != None && rw->label.lbm_width > 0 ) + { + /* TODO: handle pixmaps */ + XCopyPlane(dpy, left_bitmap, win, gc, + 0,0, rw->label.lbm_width, rw->label.lbm_height, + (int) rw->label.internal_width*2 + bs(rw), + (int) rw->label.internal_height + rw->label.lbm_y, + (u_long) 1L) ; + } + + /* Finally, the button itself */ + ((RadioWidgetClass)(w->core.widget_class))->radio_class.drawDiamond(w) ; +} + + + + +/************************************************************ + * + * Set specified arguments into widget + * + ***********************************************************/ + + +/* ARGSUSED */ +static Boolean +RadioSetValues (Widget current, + Widget request, + Widget new, + ArgList args, + Cardinal *num_args) +{ + RadioWidget oldrw = (RadioWidget) current; + RadioWidget newrw = (RadioWidget) new; + + /* Need to find out if the size of the widget changed. Set new size + * if it did and resize is permitted. One way to determine of the + * widget changed size would be to scan the args list. Another way + * is to compare the old and new widgets and see if any of several + * size-related fields have been changed. The Label widget chose the + * former method, but I choose the latter. + */ + + if( newrw->label.resize && + ( newrw->core.width != oldrw->core.width || + newrw->core.height != oldrw->core.height || + newrw->core.border_width != oldrw->core.border_width ) ) + { + RadioSize(newrw, &newrw->core.width, &newrw->core.height) ; + } + + return FALSE ; +} + +static XtGeometryResult +RadioQueryGeometry (Widget w, + XtWidgetGeometry *intended, + XtWidgetGeometry *preferred) +{ + RadioWidget rw = (RadioWidget) w; + + preferred->request_mode = CWWidth | CWHeight; + RadioSize(rw, &preferred->width, &preferred->height) ; + + if ( ((intended->request_mode & (CWWidth | CWHeight)) + == (CWWidth | CWHeight)) && + intended->width == preferred->width && + intended->height == preferred->height) + return XtGeometryYes; + else if (preferred->width == w->core.width && + preferred->height == w->core.height) + return XtGeometryNo; + else + return XtGeometryAlmost; +} + + + + + +/************************************************************ + * + * Action Procedures + * + ************************************************************/ + +/* + * Draw the highlight border around the widget. The Command widget + * did this by drawing through a mask. We do it by just drawing the + * border. + */ + +static void +DrawHighlight (Widget w, + GC gc) +{ + RadioWidget rw = (RadioWidget)w; + XRectangle rects[4] ; + Dimension ht = rw->command.highlight_thickness ; + + if( ht <= 0 || + ht > rw->core.width/2 || + ht > rw->core.height/2 ) + return ; + + if( ! XtIsRealized(w) ) + return ; + + rects[0].x = 0 ; rects[0].y = 0 ; + rects[0].width = rw->core.width ; rects[0].height = ht ; + rects[1].x = 0 ; rects[1].y = rw->core.height - ht ; + rects[1].width = rw->core.width ; rects[1].height = ht ; + rects[2].x = 0 ; rects[2].y = ht ; + rects[2].width = ht ; rects[2].height = rw->core.height - ht*2 ; + rects[3].x = rw->core.width - ht ; rects[3].y = ht ; + rects[3].width = ht ; rects[3].height = rw->core.height - ht*2 ; + XFillRectangles( XtDisplay(w), XtWindow(w), gc, rects, 4) ; +} + +static void +RadioHighlight (Widget w, + XEvent *event, + String *params, + Cardinal *num_params) +{ + RadioWidget rw = (RadioWidget)w; + DrawHighlight(w, rw->command.normal_GC) ; +} + + +static void +RadioUnhighlight (Widget w, + XEvent *event, + String *params, + Cardinal *num_params) +{ + RadioWidget rw = (RadioWidget)w; + DrawHighlight(w, rw->command.inverse_GC) ; +} + + +/* ARGSUSED */ +void +RadioSet (Widget w, + XEvent *event, + String *params, /* unused */ + Cardinal *num_params) /* unused */ +{ + RadioWidget rw = (RadioWidget)w; + RadioWidgetClass class = (RadioWidgetClass) w->core.widget_class ; + + if( rw->command.set ) + return ; + + rw->command.set = TRUE ; + if( XtIsRealized(w) ) + class->radio_class.drawDiamond(w) ; +} + + +/* ARGSUSED */ +void +RadioUnset (Widget w, + XEvent *event, + String *params, /* unused */ + Cardinal *num_params) /* unused */ +{ + RadioWidget rw = (RadioWidget)w; + RadioWidgetClass class = (RadioWidgetClass) w->core.widget_class ; + + if( ! rw->command.set ) + return ; + + rw->command.set = FALSE ; + if( XtIsRealized(w) ) + class->radio_class.drawDiamond(w) ; +} + + + + +/************************************************************ + * + * Internal Procedures + * + ************************************************************/ + + +/* Size of widget. Width is size of box plus width of border around + * box plus width of label plus three margins plus the size of the left + * bitmap, if any. Height is max(box,bitmap,label) plus two margins. + */ + +static void +RadioSize (RadioWidget rw, + Dimension *w, + Dimension *h) +{ + *w = rw->label.label_width + bs(rw) + LEFT_OFFSET(rw) + + 3 * rw->label.internal_width ; + *h = Max( rw->label.label_height, bs(rw) ) + + 2 * rw->label.internal_width ; +} + + +static void +DrawDiamond (Widget w) +{ + RadioWidget rw = (RadioWidget) w ; + Display *dpy = XtDisplay(w) ; + Window win = XtWindow(w) ; + GC gc, gci ; + + XPoint pts[5] ; + Dimension del = bsize(rw)/2 ; + Position x,y ; /* diamond center */ +#ifdef _ThreeDP_h + int i=0; + Dimension s = swid(rw) ; + GC top, bot, ctr ; +#endif + gc = XtIsSensitive(w) ? rw->command.normal_GC : rw->label.gray_GC ; + + gci = rw->command.set ? rw->command.normal_GC : rw->command.inverse_GC ; + + x = rw->label.internal_width + bs(rw)/2 ; + y = rw->core.height/2 ; + +#ifdef _ThreeDP_h + if( ! rw->command.set ) { + top = rw->threeD.top_shadow_GC ; + bot = rw->threeD.bot_shadow_GC ; + ctr = gc ; /* TODO */ + } else { + top = rw->threeD.bot_shadow_GC ; + bot = rw->threeD.top_shadow_GC ; + ctr = gc ; /* TODO */ + } +#endif + + pts[0].x = x - del ; + pts[0].y = y ; + pts[1].x = x ; + pts[1].y = y - del ; + pts[2].x = x + del ; + pts[2].y = y ; + pts[3].x = x ; + pts[3].y = y + del ; + pts[4] = pts[0] ; + XFillPolygon(dpy,win,gci, pts,4, Convex, CoordModeOrigin) ; + +#ifdef _ThreeDP_h + for(i=0; i + +/* Resources: + + Name Class RepType Default Value + ---- ----- ------- ------------- + radioGroup RadioGroup Widget NULL + radioData RadioData Pointer (XPointer) Widget + state State Boolean Off + background Background Pixel XtDefaultBackground + bitmap Pixmap Pixmap None + border BorderColor Pixel XtDefaultForeground + borderWidth BorderWidth Dimension 1 + callback Callback Pointer NULL + cursor Cursor Cursor None + destroyCallback Callback Pointer NULL + font Font XFontStructx* XtDefaultFont + foreground Foreground Pixel XtDefaultForeground + height Height Dimension text height + highlightThickness Thickness Dimension 2 + insensitiveBorder sensitive Pixmap Gray + internalHeight Height Dimension 2 + internalWidth Width Dimension 4 + justify Justify XtJustify XtJustifyCenter + label Label String NULL + mappedWhenManaged MappedWhenManaged Boolean True + resize Resize Boolean True + sensitive Sensitive Boolean True + width Width Dimension text width + x Position Position 0 + y Position Position 0 + +*/ + +/* + * These should be in StringDefs.h but aren't so we will define + * them here if they are needed. + */ + + +extern WidgetClass radioWidgetClass; + +typedef struct _RadioClassRec *RadioWidgetClass; +typedef struct _RadioRec *RadioWidget; + + +/************************************************************ + * + * Public Functions + * + ************************************************************/ + +#endif /* _XawRadio_h */ diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwradioP.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwradioP.h Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,116 @@ +/* Radio Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* + * RadioP.h - Private definitions for Radio widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: June 30, 1997 + * + */ + +#ifndef _XawRadioP_h +#define _XawRadioP_h + +#include "xlwradio.h" +#include + +/*********************************************************************** + * + * Radio Widget Private Data + * + ***********************************************************************/ + +#define streq(a, b) ( strcmp((a), (b)) == 0 ) + +typedef void (*XawDiamondProc) (Widget); + +void RadioSet (Widget w, + XEvent *event, + String *params, /* unused */ + Cardinal *num_params); /* unused */ + +void RadioUnset (Widget w, + XEvent *event, + String *params, /* unused */ + Cardinal *num_params); /* unused */ + +/************************************ + * + * Class structure + * + ***********************************/ + + /* New fields for the Radio widget class record */ +typedef struct _RadioClass { + Dimension dsize ; /* diamond size */ + XawDiamondProc drawDiamond ; + /* TODO: 3-d and xaw-xpm features? */ + XtPointer extension; +} RadioClassPart; + +#define XtInheritDrawDiamond ((XawDiamondProc)_XtInherit) + + /* Full class record declaration */ +typedef struct _RadioClassRec { + CoreClassPart core_class; + SimpleClassPart simple_class; +#ifdef _ThreeDP_h + ThreeDClassPart threeD_class; +#endif + LabelClassPart label_class; + CommandClassPart command_class; + ToggleClassPart toggle_class; + RadioClassPart radio_class; +} RadioClassRec; + +extern RadioClassRec radioClassRec; + +/*************************************** + * + * Instance (widget) structure + * + **************************************/ + + /* New fields for the Radio widget record */ +typedef struct { + /* resources */ + /* TODO: 3-d and xaw-xpm features? */ + + /* private data */ + XtPointer extension; +} RadioPart; + + /* Full widget declaration */ +typedef struct _RadioRec { + CorePart core; + SimplePart simple; +#ifdef _ThreeDP_h + ThreeDPart threeD; +#endif + LabelPart label; + CommandPart command; + TogglePart toggle; + RadioPart radio; +} RadioRec; + +#endif /* _XawRadioP_h */ diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwtabs.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwtabs.c Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,2069 @@ + /* Tabs Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + + This file is part of XEmacs. + + XEmacs is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 2, or (at your option) any + later version. + + XEmacs is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with XEmacs; see the file COPYING. If not, write to + the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + + /* Synched up with: Tabs.c 1.23 */ + + /* + * Tabs.c - Index Tabs composite widget + * + * Author: Edward A. Falk + * falk@falconer.vip.best.com + * + * Date: July 29, 1997 + * + * + * Overall layout of this widget is as follows: + * + * ________ ,---------. _________ + * | label || Label || Label | \ tabs + * |________|| ||_________| / + * |+----------------------------+| \ + * || || | + * || child widget window || > frame + * |+----------------------------+| | + * +------------------------------+ / + * + * The height of the tabs includes the shadow width, top and bottom + * margins, and the height of the text. + * + * The height of the frame includes the top and bottom shadow width and the + * size of the child widget window. + * + * The tabs overlap the frame and each other vertically by the shadow + * width, so that when the topmost tab is drawn, it obliterates part of + * the frame. + */ + +/* TODO: min child height = tab height + * + */ + +#include +#include + +#include +#include +#include +#include "../src/xmu.h" +#include "xlwtabsP.h" +#include "xlwgcs.h" + +#define MIN_WID 10 +#define MIN_HGT 10 +#define INDENT 3 /* tabs indented from edge by this much */ +#define SPACING 0 /* distance between tabs */ +#define SHADWID 1 /* default shadow width */ +#define TABDELTA 2 /* top tab grows this many pixels */ +#define TABLDELTA 2 /* top tab label offset this many pixels */ + + +/**************************************************************** + * + * IndexTabs Resources + * + ****************************************************************/ + +static char defaultTranslations[] = "\ + : select() \n\ + : highlight() \n\ + : unhighlight() \n\ + Page_Up: page(up) \n\ + KP_Page_Up: page(up) \n\ + Prior: page(up) \n\ + KP_Prior: page(up) \n\ + Page_Down: page(down) \n\ + KP_Page_Down: page(down) \n\ + Next: page(down) \n\ + KP_Next: page(down) \n\ + Home: page(home) \n\ + KP_Home: page(home) \n\ + End: page(end) \n\ + KP_End: page(end) \n\ + Up: highlight(up) \n\ + KP_Up: highlight(up) \n\ + Down: highlight(down) \n\ + KP_Down: highlight(down) \n\ + : page(select) \n\ + " ; + +static char accelTable[] = " #augment\n\ + Page_Up: page(up) \n\ + KP_Page_Up: page(up) \n\ + Prior: page(up) \n\ + KP_Prior: page(up) \n\ + Page_Down: page(down) \n\ + KP_Page_Down: page(down) \n\ + Next: page(down) \n\ + KP_Next: page(down) \n\ + Home: page(home) \n\ + KP_Home: page(home) \n\ + End: page(end) \n\ + KP_End: page(end) \n\ + Up: highlight(up) \n\ + KP_Up: highlight(up) \n\ + Down: highlight(down) \n\ + KP_Down: highlight(down) \n\ + : page(select) \n\ + " ; +static XtAccelerators defaultAccelerators ; + +#define offset(field) XtOffsetOf(TabsRec, tabs.field) +static XtResource resources[] = { + + {XtNselectInsensitive, XtCSelectInsensitive, XtRBoolean, sizeof(Boolean), + offset(selectInsensitive), XtRImmediate, (XtPointer) True}, + {XtNfont, XtCFont, XtRFontStruct, sizeof(XFontStruct *), + offset(font), XtRString, (XtPointer) XtDefaultFont}, + {XtNinternalWidth, XtCWidth, XtRDimension, sizeof(Dimension), + offset(internalWidth), XtRImmediate, (XtPointer)4 }, + {XtNinternalHeight, XtCHeight, XtRDimension, sizeof(Dimension), + offset(internalHeight), XtRImmediate, (XtPointer)4 }, + {XtNborderWidth, XtCBorderWidth, XtRDimension, sizeof(Dimension), + XtOffsetOf(RectObjRec,rectangle.border_width), XtRImmediate, (XtPointer)0}, + {XtNtopWidget, XtCTopWidget, XtRWidget, sizeof(Widget), + offset(topWidget), XtRImmediate, NULL}, + {XtNcallback, XtCCallback, XtRCallback, sizeof(XtPointer), + offset(callbacks), XtRCallback, NULL}, + {XtNpopdownCallback, XtCCallback, XtRCallback, sizeof(XtPointer), + offset(popdownCallbacks), XtRCallback, NULL}, + {XtNbeNiceToColormap, XtCBeNiceToColormap, XtRBoolean, sizeof(Boolean), + offset(be_nice_to_cmap), XtRImmediate, (XtPointer) True}, + {XtNtopShadowContrast, XtCTopShadowContrast, XtRInt, sizeof(int), + offset(top_shadow_contrast), XtRImmediate, (XtPointer) 20}, + {XtNbottomShadowContrast, XtCBottomShadowContrast, XtRInt, sizeof(int), + offset(bot_shadow_contrast), XtRImmediate, (XtPointer) 40}, + {XtNinsensitiveContrast, XtCInsensitiveContrast, XtRInt, sizeof(int), + offset(insensitive_contrast), XtRImmediate, (XtPointer) 33}, + {XtNaccelerators, XtCAccelerators, XtRAcceleratorTable,sizeof(XtTranslations), + XtOffsetOf(TabsRec,core.accelerators), XtRString, accelTable}, +}; +#undef offset + + + + /* constraint resources */ + +#define offset(field) XtOffsetOf(TabsConstraintsRec, tabs.field) +static XtResource tabsConstraintResources[] = { + {XtNtabLabel, XtCLabel, XtRString, sizeof(String), + offset(label), XtRString, NULL}, + {XtNtabLeftBitmap, XtCLeftBitmap, XtRBitmap, sizeof(Pixmap), + offset(left_bitmap), XtRImmediate, None}, + {XtNtabForeground, XtCForeground, XtRPixel, sizeof(Pixel), + offset(foreground), XtRString, (XtPointer) XtDefaultForeground}, + {XtNresizable, XtCResizable, XtRBoolean, sizeof(Boolean), + offset(resizable), XtRImmediate, (XtPointer) True}, +} ; +#undef offset + + + + +#if !NeedFunctionPrototypes + + /* FORWARD REFERENCES: */ + + /* member functions */ + +static void TabsClassInit(); +static void TabsInit(); +static void TabsResize(); +static void TabsExpose(); +static void TabsDestroy(); +static void TabsRealize(); +static Boolean TabsSetValues(); +static XtGeometryResult TabsQueryGeometry(); +static XtGeometryResult TabsGeometryManager(); +static void TabsChangeManaged(); +static void TabsConstraintInitialize() ; +static Boolean TabsConstraintSetValues() ; + + /* action procs */ + +static void TabsSelect() ; +static void TabsPage() ; +static void TabsHighlight() ; +static void TabsUnhighlight() ; + + /* internal privates */ + +static void TabsAllocGCs() ; /* get rendering GCs */ +static void TabsFreeGCs() ; /* return rendering GCs */ +static void DrawTabs() ; /* draw all tabs */ +static void DrawTab() ; /* draw one index tab */ +static void DrawFrame() ; /* draw frame around contents */ +static void DrawTrim() ; /* draw trim around a tab */ +static void DrawBorder() ; /* draw border */ +static void DrawHighlight() ; /* draw highlight */ +static void UndrawTab() ; /* undraw interior of a tab */ +static void TabWidth() ; /* recompute tab size */ +static void GetPreferredSizes() ; /* query all children for their sizes */ +static void MaxChild() ; /* find max preferred child size */ +static int PreferredSize() ; /* compute preferred size */ +static int PreferredSize2() ; /* compute preferred size */ +static int PreferredSize3() ; /* compute preferred size */ +static void MakeSizeRequest() ; /* try to change size */ +static void getBitmapInfo() ; +static int TabLayout() ; /* lay out tabs */ +static void TabsShuffleRows() ; /* bring current tab to bottom row */ + +static void TabsAllocFgGC() ; +static void TabsAllocGreyGC() ; + +#else + +static void TabsClassInit(void) ; +static void TabsInit( Widget req, Widget new, ArgList, Cardinal *nargs) ; +static void TabsConstraintInitialize(Widget, Widget, ArgList, Cardinal *) ; +static void TabsRealize(Widget, Mask *, XSetWindowAttributes *) ; +static void TabsDestroy( Widget w) ; +static void TabsResize( Widget w) ; +static void TabsExpose( Widget w, XEvent *event, Region region) ; +static Boolean TabsSetValues(Widget, Widget, Widget, ArgList, Cardinal *) ; +static Boolean TabsConstraintSetValues(Widget, Widget, Widget, + ArgList, Cardinal *) ; +static XtGeometryResult TabsQueryGeometry(Widget, + XtWidgetGeometry *, XtWidgetGeometry *) ; +static XtGeometryResult TabsGeometryManager(Widget, + XtWidgetGeometry *, XtWidgetGeometry *) ; +static void TabsChangeManaged( Widget w) ; + +static void TabsSelect(Widget, XEvent *, String *, Cardinal *) ; +static void TabsPage(Widget, XEvent *, String *, Cardinal *) ; +static void TabsHighlight(Widget, XEvent *, String *, Cardinal *) ; +static void TabsUnhighlight(Widget, XEvent *, String *, Cardinal *) ; + +static void DrawTabs( TabsWidget tw, Bool labels) ; +static void DrawTab( TabsWidget tw, Widget child, Bool labels) ; +static void DrawFrame( TabsWidget tw) ; +static void DrawTrim( TabsWidget, int x, int y, + int wid, int hgt, Bool bottom, Bool undraw) ; +static void DrawBorder( TabsWidget tw, Widget child, Bool undraw) ; +static void DrawHighlight( TabsWidget tw, Widget child, Bool undraw) ; +static void UndrawTab( TabsWidget tw, Widget child) ; + +static void TabWidth( Widget w) ; +static int TabLayout( TabsWidget, int wid, int hgt, Dimension *r_hgt, + Bool query_only) ; +static void GetPreferredSizes(TabsWidget) ; +static void MaxChild(TabsWidget) ; +static void TabsShuffleRows( TabsWidget tw) ; +static int PreferredSize( TabsWidget, + Dimension *reply_width, Dimension *reply_height, + Dimension *reply_cw, Dimension *reply_ch) ; +static int PreferredSize2( TabsWidget, int cw, int ch, + Dimension *rw, Dimension *rh) ; +static int PreferredSize3( TabsWidget, int wid, int hgt, + Dimension *rw, Dimension *rh) ; +static void MakeSizeRequest(TabsWidget) ; + +static void TabsAllocGCs(TabsWidget) ; +static void TabsFreeGCs(TabsWidget) ; +static void getBitmapInfo( TabsWidget tw, TabsConstraints tab) ; +static void TabsAllocFgGC( TabsWidget tw) ; +static void TabsAllocGreyGC( TabsWidget tw) ; + +#endif + +#define AddRect(i,xx,yy,w,h) \ + do{rects[(i)].x=(xx); rects[i].y=(yy); \ + rects[i].width=(w); rects[i].height=(h);}while(0) + +static XtActionsRec actionsList[] = + { + {"select", TabsSelect}, + {"page", TabsPage}, + {"highlight", TabsHighlight}, + {"unhighlight", TabsUnhighlight}, + } ; + + +/**************************************************************** +* +* Full class record constant +* +****************************************************************/ + +#ifndef NEED_MOTIF +#define SuperClass (&constraintClassRec) +#else +#define SuperClass (&xmManagerClassRec) +#endif + +TabsClassRec tabsClassRec = { + { +/* core_class fields */ + /* superclass */ (WidgetClass) SuperClass, + /* class_name */ "Tabs", + /* widget_size */ sizeof(TabsRec), + /* class_initialize */ TabsClassInit, + /* class_part_init */ NULL, /* TODO? */ + /* class_inited */ FALSE, + /* initialize */ TabsInit, + /* initialize_hook */ NULL, + /* realize */ TabsRealize, + /* actions */ actionsList, + /* num_actions */ XtNumber(actionsList), + /* resources */ resources, + /* num_resources */ XtNumber(resources), + /* xrm_class */ NULLQUARK, + /* compress_motion */ TRUE, + /* compress_exposure */ TRUE, + /* compress_enterleave*/ TRUE, + /* visible_interest */ FALSE, + /* destroy */ TabsDestroy, + /* resize */ TabsResize, + /* expose */ TabsExpose, + /* set_values */ TabsSetValues, + /* set_values_hook */ NULL, + /* set_values_almost */ XtInheritSetValuesAlmost, + /* get_values_hook */ NULL, + /* accept_focus */ NULL, + /* version */ XtVersion, + /* callback_private */ NULL, + /* tm_table */ defaultTranslations, + /* query_geometry */ TabsQueryGeometry, + /* display_accelerator*/ XtInheritDisplayAccelerator, + /* extension */ NULL + }, + { +/* composite_class fields */ + /* geometry_manager */ TabsGeometryManager, + /* change_managed */ TabsChangeManaged, + /* insert_child */ XtInheritInsertChild, /* TODO? */ + /* delete_child */ XtInheritDeleteChild, /* TODO? */ + /* extension */ NULL + }, + { +/* constraint_class fields */ + /* subresources */ tabsConstraintResources, + /* subresource_count */ XtNumber(tabsConstraintResources), + /* constraint_size */ sizeof(TabsConstraintsRec), + /* initialize */ TabsConstraintInitialize, + /* destroy */ NULL, + /* set_values */ TabsConstraintSetValues, + /* extension */ NULL, + }, +#ifdef NEED_MOTIF +/* Manager Class fields */ + { + /* translations */ NULL, + /* syn_resources */ NULL, + /* num_syn_resources */ 0, + /* syn_constraint_resources */ NULL, + /* num_syn_constraint_resources */ 0, + /* parent_process */ XmInheritParentProcess, + /* extension */ NULL + }, +#endif + { +/* Tabs class fields */ + /* extension */ NULL, + } +}; + +WidgetClass tabsWidgetClass = (WidgetClass)&tabsClassRec; + + + +#ifdef DEBUG +#ifdef __STDC__ +#define assert(e) \ + if(!(e)) fprintf(stderr,"yak! %s at %s:%d\n",#e,__FILE__,__LINE__) +#else +#define assert(e) \ + if(!(e)) fprintf(stderr,"yak! e at %s:%d\n",__FILE__,__LINE__) +#endif +#else +#define assert(e) +#endif + + + + +/**************************************************************** + * + * Member Procedures + * + ****************************************************************/ + +static void +TabsClassInit(void) +{ + defaultAccelerators = XtParseAcceleratorTable(accelTable) ; + /* TODO: register converter for labels? */ +} + + + + /* Init a newly created tabs widget. Compute height of tabs + * and optionally compute size of widget. */ + +/* ARGSUSED */ + +static void +TabsInit(Widget request, Widget new, ArgList args, Cardinal *num_args) +{ + TabsWidget newTw = (TabsWidget)new; + + newTw->tabs.numRows = 0 ; + newTw->tabs.displayChildren = 0; + + GetPreferredSizes(newTw) ; + + /* height is easy, it's the same for all tabs: + * TODO: font height + height of tallest bitmap. + */ + newTw->tabs.tab_height = 2 * newTw->tabs.internalHeight + SHADWID ; + + if( newTw->tabs.font != NULL ) + newTw->tabs.tab_height += newTw->tabs.font->max_bounds.ascent + + newTw->tabs.font->max_bounds.descent ; + + /* GC allocation is deferred until XtRealize() */ + + /* if size not explicitly set, set it to our preferred size now. */ + + if( request->core.width == 0 || request->core.height == 0 ) + { + Dimension w,h ; + PreferredSize(newTw, &w, &h, NULL,NULL) ; + if( request->core.width == 0 ) new->core.width = w ; + if( request->core.height == 0 ) new->core.height = h ; + XtClass(new)->core_class.resize(new) ; + } + + /* defer GC allocation, etc., until Realize() time. */ + newTw->tabs.foregroundGC = + newTw->tabs.backgroundGC = + newTw->tabs.greyGC = + newTw->tabs.topGC = + newTw->tabs.botGC = None ; + + newTw->tabs.grey50 = None ; + + newTw->tabs.needs_layout = False ; + + newTw->tabs.hilight = NULL ; + +#ifdef NEED_MOTIF + newTw->manager.navigation_type = XmTAB_GROUP ; + newTw->manager.traversal_on = True ; +#endif +} + + + /* Init the constraint part of a new tab child. Compute the + * size of the tab. + */ +/* ARGSUSED */ +static void +TabsConstraintInitialize(Widget request, Widget new, + ArgList args, Cardinal *num_args) +{ + TabsConstraints tab = (TabsConstraints) new->core.constraints ; + tab->tabs.greyAlloc = False ; /* defer allocation of pixel */ + tab->tabs.queried = False ; /* defer size query */ + + getBitmapInfo((TabsWidget)XtParent(new), tab) ; + TabWidth(new) ; +} + + + + /* Called when tabs widget first realized. Create the window + * and allocate the GCs + */ + +static void +TabsRealize(Widget w, Mask *valueMask, XSetWindowAttributes *attributes) +{ + TabsWidget tw = (TabsWidget) w; + + attributes->bit_gravity = NorthWestGravity; + *valueMask |= CWBitGravity; + + SuperClass->core_class.realize(w, valueMask, attributes); + + TabsAllocGCs(tw) ; +} + + + +static void +TabsDestroy(Widget w) +{ + TabsFreeGCs((TabsWidget)w) ; +} + + + /* Parent has resized us. This will require that the tabs be + * laid out again. + */ + +static void +TabsResize(Widget w) +{ + TabsWidget tw = (TabsWidget) w; + int i ; + int num_children = tw->composite.num_children ; + Widget *childP ; + TabsConstraints tab ; + Dimension cw,ch,bw ; + + /* Our size has now been dictated by the parent. Lay out the + * tabs, lay out the frame, lay out the children. Remember + * that the tabs overlap each other and the frame by shadowWidth. + * Also, the top tab is larger than the others, so if there's only + * one row, the widget must be made taller to accommodate this. + * + * Once the tabs are laid out, if there is more than one + * row, we may need to shuffle the rows to bring the top tab + * to the bottom row. + */ + + if( num_children > 0 && tw->composite.children != NULL ) + { + /* Loop through the tabs and assign rows & x positions */ + (void) TabLayout(tw, tw->core.width, tw->core.height, NULL, False) ; + num_children = tw->tabs.displayChildren; + + /* assign a top widget, bring it to bottom row. */ + TabsShuffleRows(tw) ; + + /* now assign child positions & sizes. Positions are all the + * same: just inside the frame. Sizes are also all the same. + */ + + tw->tabs.child_width = cw = tw->core.width - 2 * SHADWID ; + tw->tabs.child_height = ch = + tw->core.height - tw->tabs.tab_total - 2 * SHADWID ; + + + for(i=0, childP=tw->composite.children; + i < num_children; + ++i, ++childP) + if( XtIsManaged(*childP) ) + { + tab = (TabsConstraints) (*childP)->core.constraints ; + bw = tab->tabs.bwid ; + XtConfigureWidget(*childP, SHADWID,tw->tabs.tab_total+SHADWID, + cw-bw*2,ch-bw*2, bw) ; + } + if( XtIsRealized(w) ) + XClearWindow(XtDisplay((Widget)tw), XtWindow((Widget)tw)) ; + } + + tw->tabs.needs_layout = False ; +} /* Resize */ + + + + /* Redraw entire Tabs widget */ + +/* ARGSUSED */ +static void +TabsExpose(Widget w, XEvent *event, Region region) +{ + TabsWidget tw = (TabsWidget) w; + + if( tw->tabs.needs_layout ) + XtClass(w)->core_class.resize(w) ; + + DrawTabs(tw, True) ; +} + + + /* Called when any Tabs widget resources are changed. */ + +/* ARGSUSED */ +static Boolean +TabsSetValues(Widget current, Widget request, Widget new, + ArgList args, Cardinal *num_args) +{ + TabsWidget curtw = (TabsWidget) current ; + TabsWidget tw = (TabsWidget) new ; + Boolean needRedraw = False ; + Widget *childP ; + int i ; + + + if( tw->tabs.font != curtw->tabs.font || + tw->tabs.internalWidth != curtw->tabs.internalWidth || + tw->tabs.internalHeight != curtw->tabs.internalHeight ) + { + tw->tabs.tab_height = 2 * tw->tabs.internalHeight + SHADWID ; + + if( tw->tabs.font != NULL ) + tw->tabs.tab_height += tw->tabs.font->max_bounds.ascent + + tw->tabs.font->max_bounds.descent ; + + /* Tab size has changed. Resize all tabs and request a new size */ + for(i=0, childP=tw->composite.children; + i < tw->composite.num_children; + ++i, ++childP) + if( XtIsManaged(*childP) ) + TabWidth(*childP) ; + PreferredSize(tw, &tw->core.width, &tw->core.height, NULL,NULL) ; + needRedraw = True ; + tw->tabs.needs_layout = True ; + } + + /* TODO: if any color changes, need to recompute GCs and redraw */ + + if( tw->core.background_pixel != curtw->core.background_pixel || + tw->core.background_pixmap != curtw->core.background_pixmap ) + if( XtIsRealized(new) ) + { + TabsFreeGCs(tw) ; + TabsAllocGCs(tw) ; + needRedraw = True ; + } + + if( tw->core.sensitive != curtw->core.sensitive ) + needRedraw = True ; + + /* If top widget changes, need to change stacking order, redraw tabs. + * Window system will handle the redraws. + */ + + if( tw->tabs.topWidget != curtw->tabs.topWidget ) + if( XtIsRealized(tw->tabs.topWidget) ) + { + Widget w = tw->tabs.topWidget ; + TabsConstraints tab = (TabsConstraints) w->core.constraints ; + + XRaiseWindow(XtDisplay(w), XtWindow(w)) ; +#ifdef NEED_MOTIF + XtVaSetValues(curtw->tabs.topWidget, XmNtraversalOn, False, 0) ; + XtVaSetValues(w, XmNtraversalOn, True, 0) ; +#endif + + if( tab->tabs.row != tw->tabs.numRows-1 ) + TabsShuffleRows(tw) ; + + needRedraw = True ; + } + else + tw->tabs.needs_layout = True ; + + return needRedraw ; +} + + + /* Called when any child constraint resources change. */ + +/* ARGSUSED */ +static Boolean +TabsConstraintSetValues(Widget current, Widget request, Widget new, + ArgList args, Cardinal *num_args) +{ + TabsWidget tw = (TabsWidget) XtParent(new) ; + TabsConstraints ctab = (TabsConstraints) current->core.constraints ; + TabsConstraints tab = (TabsConstraints) new->core.constraints ; + + + /* if label changes, need to re-layout the entire widget */ + /* if foreground changes, need to redraw tab label */ + + /* TODO: only need resize of new bitmap has different dimensions + * from old bitmap. + */ + + if( tab->tabs.label != ctab->tabs.label || /* Tab size has changed. */ + tab->tabs.left_bitmap != ctab->tabs.left_bitmap ) + { + TabWidth(new) ; + tw->tabs.needs_layout = True ; + + if( tab->tabs.left_bitmap != ctab->tabs.left_bitmap ) + getBitmapInfo(tw, tab) ; + + /* If there are no subclass ConstraintSetValues procedures remaining + * to be invoked, and if the preferred size has changed, ask + * for a resize. + */ + if( XtClass((Widget)tw) == tabsWidgetClass ) + MakeSizeRequest(tw) ; + } + + + /* The child widget itself never needs a redisplay, but the parent + * Tabs widget might. + */ + + if( XtIsRealized(new) ) + { + if( tw->tabs.needs_layout ) { + XClearWindow(XtDisplay((Widget)tw), XtWindow((Widget)tw)) ; + XtClass(tw)->core_class.expose((Widget)tw,NULL,None) ; + } + + else if( tab->tabs.foreground != ctab->tabs.foreground ) + DrawTab(tw, new, True) ; + } + + return False ; +} + + + +/* + * Return preferred size. Happily accept anything >= our preferred size. + * (TODO: is that the right thing to do? Should we always return "almost" + * if offerred more than we need?) + */ + +static XtGeometryResult +TabsQueryGeometry(Widget w, + XtWidgetGeometry *intended, XtWidgetGeometry *preferred) +{ + register TabsWidget tw = (TabsWidget)w ; + XtGeometryMask mode = intended->request_mode ; + + preferred->request_mode = CWWidth | CWHeight ; + PreferredSize(tw, &preferred->width, &preferred->height, NULL,NULL) ; + + if( (!(mode & CWWidth) || intended->width == w->core.width) && + (!(mode & CWHeight) || intended->height == w->core.height) ) + return XtGeometryNo ; + +#ifdef COMMENT + if( (!(mode & CWWidth) || intended->width >= preferred->width) && + (!(mode & CWHeight) || intended->height >= preferred->height) ) + return XtGeometryYes; +#endif /* COMMENT */ + + return XtGeometryAlmost; +} + + + +/* + * Geometry Manager; called when a child wants to be resized. + */ + +static XtGeometryResult +TabsGeometryManager(Widget w, XtWidgetGeometry *req, XtWidgetGeometry *reply) +{ + TabsWidget tw = (TabsWidget) XtParent(w); + Dimension s = SHADWID ; + TabsConstraints tab = (TabsConstraints)w->core.constraints; + XtGeometryResult result ; + + /* Position request always denied */ + + if( ((req->request_mode & CWX) && req->x != w->core.x) || + ((req->request_mode & CWY) && req->y != w->core.y) || + !tab->tabs.resizable ) + return XtGeometryNo ; + + /* Make all three fields in the request valid */ + if( !(req->request_mode & CWWidth) ) + req->width = w->core.width; + if( !(req->request_mode & CWHeight) ) + req->height = w->core.height; + if( !(req->request_mode & CWBorderWidth) ) + req->border_width = w->core.border_width; + + if( req->width == w->core.width && + req->height == w->core.height && + req->border_width == w->core.border_width ) + return XtGeometryNo ; + + /* updated cached preferred size of the child */ + tab->tabs.bwid = req->border_width ; + tab->tabs.wid = req->width + req->border_width * 2 ; + tab->tabs.hgt = req->height + req->border_width * 2 ; + MaxChild(tw) ; + + + /* Size changes must see if the new size can be accommodated. + * The Tabs widget keeps all of its children the same + * size. A request to shrink will be accepted only if the + * new size is still big enough for all other children. A + * request to shrink that is not big enough for all children + * returns an "almost" response with the new proposed size. + * A request to grow will be accepted only if the Tabs parent can + * grow to accommodate. + * + * TODO: + * We could get fancy here and re-arrange the tabs if it is + * necessary to compromise with the parent, but we'll save that + * for another day. + */ + + if (req->request_mode & (CWWidth | CWHeight | CWBorderWidth)) + { + Dimension rw,rh ; /* child's requested width, height */ + Dimension cw,ch ; /* children's preferred size */ + Dimension aw,ah ; /* available size we can give child */ + Dimension th ; /* space used by tabs */ + Dimension wid,hgt ; /* Tabs widget size */ + + rw = tab->tabs.wid ; + rh = tab->tabs.hgt ; + + /* find out what the resulting preferred size would be */ + +#ifdef COMMENT + MaxChild(tw, &cw, &ch) ; +#endif /* COMMENT */ + PreferredSize2(tw, tw->tabs.max_cw,tw->tabs.max_ch, &wid, &hgt) ; + + /* Ask to be resized to accommodate. */ + + if( wid != tw->core.width || hgt != tw->core.height ) + { + Dimension oldWid = tw->core.width, oldHgt = tw->core.height ; + XtWidgetGeometry myrequest, myreply ; + + myrequest.width = wid ; + myrequest.height = hgt ; + myrequest.request_mode = CWWidth | CWHeight ; + + /* If child is only querying, or if we're going to have to + * offer the child a compromise, then make this a query only. + */ + + if( (req->request_mode & XtCWQueryOnly) || rw < cw || rh < ch ) + myrequest.request_mode |= XtCWQueryOnly ; + + result = XtMakeGeometryRequest((Widget)tw, &myrequest, &myreply) ; + + /* !$@# Box widget changes the core size even if QueryOnly + * is set. I'm convinced this is a bug. At any rate, to work + * around the bug, we need to restore the core size after every + * query geometry request. This is only partly effective, + * as there may be other boxes further up the tree. + */ + if( myrequest.request_mode & XtCWQueryOnly ) { + tw->core.width = oldWid ; + tw->core.height = oldHgt ; + } + + /* based on the parent's response, determine what the + * resulting Tabs widget size would be. + */ + + switch( result ) { + case XtGeometryYes: + case XtGeometryDone: + break ; + + case XtGeometryNo: + wid = tw->core.width ; + hgt = tw->core.height ; + break ; + + case XtGeometryAlmost: + wid = myreply.width ; + hgt = myreply.height ; + } + } + + /* Within the constraints imposed by the parent, what is + * the max size we can give the child? + */ + (void) TabLayout(tw, wid, hgt, &th, True) ; + aw = wid - 2*s ; + ah = hgt - th - 2*s ; + + /* OK, make our decision. If requested size is >= max sibling + * preferred size, AND requested size <= available size, then + * we accept. Otherwise, we offer a compromise. + */ + + if( rw == aw && rh == ah ) + { + /* Acceptable. If this wasn't a query, change *all* children + * to this size. + */ + if( req->request_mode & XtCWQueryOnly ) + return XtGeometryYes ; + else + { + Widget *childP = tw->composite.children ; + int i,bw ; + w->core.border_width = req->border_width ; + for(i=tw->tabs.displayChildren; --i >= 0; ++childP) + if( XtIsManaged(*childP) ) + { + bw = (*childP)->core.border_width ; + XtConfigureWidget(*childP, s,tw->tabs.tab_total+s, + rw-2*bw, rh-2*bw, bw) ; + } +#ifdef COMMENT + /* TODO: under what conditions will we need to redraw? */ + XClearWindow(XtDisplay((Widget)tw), XtWindow((Widget)tw)) ; + XtClass(tw)->core_class.expose((Widget)tw,NULL,NULL) ; +#endif /* COMMENT */ + return XtGeometryDone ; + } + } + + /* Cannot grant child's request. Describe what we *can* do + * and return counter-offer. + */ + reply->width = aw - 2 * req->border_width ; + reply->height = ah - 2 * req->border_width ; + reply->border_width = req->border_width ; + reply->request_mode = CWWidth | CWHeight | CWBorderWidth ; + return XtGeometryAlmost ; + } + + return XtGeometryYes ; +} + + + + + /* The number of children we manage has changed; recompute + * size from scratch. + */ + +static void +TabsChangeManaged(Widget w) +{ + TabsWidget tw = (TabsWidget)w ; + Widget *childP = tw->composite.children ; + int i ; + + if( tw->tabs.topWidget != NULL && + ( !XtIsManaged(tw->tabs.topWidget) || + tw->tabs.topWidget->core.being_destroyed ) ) + tw->tabs.topWidget = NULL ; + + GetPreferredSizes(tw) ; + MakeSizeRequest(tw) ; + + XtClass(w)->core_class.resize(w) ; + if( XtIsRealized(w) ) + { + Display *dpy = XtDisplay(w) ; + XClearWindow(dpy, XtWindow(w)) ; + XtClass(w)->core_class.expose(w,NULL,NULL) ; + + /* make sure the top widget stays on top. This requires + * making sure that all new children are realized first. + */ + if( tw->tabs.topWidget != NULL && XtIsRealized(tw->tabs.topWidget) ) + { + for(i=tw->tabs.displayChildren; --i >= 0; ++childP) + if( !XtIsRealized(*childP) ) + XtRealizeWidget(*childP) ; + + XRaiseWindow(dpy, XtWindow(tw->tabs.topWidget)) ; + } + } + +#ifdef NEED_MOTIF + /* Only top widget may receive input */ + + for(childP = tw->composite.children, i=tw->composite.num_children; + --i >= 0; + ++childP) + { + XtVaSetValues(*childP, XmNtraversalOn, False, 0) ; + } + + if( tw->tabs.topWidget != NULL ) + XtVaSetValues(tw->tabs.topWidget, XmNtraversalOn, True, 0) ; +#endif + + + +} + + + + +/**************************************************************** + * + * Action Procedures + * + ****************************************************************/ + + + /* User clicks on a tab, figure out which one it was. */ + +/* ARGSUSED */ +static void +TabsSelect(Widget w, XEvent *event, String *params, Cardinal *num_params) +{ + TabsWidget tw = (TabsWidget) w ; + Widget *childP ; + Position x,y ; + Dimension h = tw->tabs.tab_height ; + int i ; + +#ifdef NEED_MOTIF + XmProcessTraversal (w, XmTRAVERSE_CURRENT) ; +#endif + + /* TODO: is there an Xmu function or something to do this instead? */ + switch( event->type ) { + case ButtonPress: + case ButtonRelease: + x = event->xbutton.x ; y = event->xbutton.y ; break ; + case KeyPress: + case KeyRelease: + x = event->xkey.x ; y = event->xkey.y ; break ; + default: + return ; + } + + /* TODO: determine which tab was clicked, if any. Set that + * widget to be top of stacking order with XawTabsSetTop(). + */ + for(i=0, childP=tw->composite.children; + i < tw->tabs.displayChildren; + ++i, ++childP) + if( XtIsManaged(*childP) ) + { + TabsConstraints tab = (TabsConstraints)(*childP)->core.constraints; + if( x > tab->tabs.x && x < tab->tabs.x + tab->tabs.width && + y > tab->tabs.y && y < tab->tabs.y + h ) + { + if( *childP != tw->tabs.topWidget && + (XtIsSensitive(*childP) || tw->tabs.selectInsensitive) ) + XawTabsSetTop(*childP, True) ; + break ; + } + } +} + + + /* User hits a key */ + +static void +TabsPage(Widget w, XEvent *event, String *params, Cardinal *num_params) +{ + TabsWidget tw = (TabsWidget) w ; + Widget newtop ; + Widget *childP ; + int idx ; + int i ; + int nc = tw->composite.num_children ; + + if( nc <= 0 ) + return ; + + if( *num_params < 1 ) { + XtAppWarning(XtWidgetToApplicationContext(w), + "Tabs: page() action called with no arguments") ; + return ; + } + + if( tw->tabs.topWidget == NULL ) + tw->tabs.topWidget = tw->composite.children[0] ; + + for(idx=0, childP=tw->composite.children; idx < nc; ++idx, ++childP ) + if( tw->tabs.topWidget == *childP ) + break ; + + switch( params[0][0] ) { + case 'u': /* up */ + case 'U': + if( idx == 0 ) + idx = nc ; + newtop = tw->composite.children[idx-1] ; + break ; + + case 'd': /* down */ + case 'D': + if( ++idx >= nc ) + idx = 0 ; + newtop = tw->composite.children[idx] ; + break ; + + case 'h': + case 'H': + newtop = tw->composite.children[0] ; + break ; + + case 'e': + case 'E': + newtop = tw->composite.children[nc-1] ; + break ; + + case 's': /* selected */ + case 'S': + if( (newtop = tw->tabs.hilight) == NULL ) + return ; + break ; + } + + XawTabsSetTop(newtop, True) ; +} + + + /* User hits up/down key */ + +static void +TabsHighlight(Widget w, XEvent *event, String *params, Cardinal *num_params) +{ + TabsWidget tw = (TabsWidget) w ; + Widget newhl ; + Widget *childP ; + int idx ; + int i ; + int nc = tw->composite.num_children ; + + if( nc <= 0 ) + return ; + + if( *num_params < 1 ) + { + if( tw->tabs.hilight != NULL ) + DrawHighlight(tw, tw->tabs.hilight, False) ; + return ; + } + + if( tw->tabs.hilight == NULL ) + newhl = tw->composite.children[0] ; + + else + { + for(idx=0, childP=tw->composite.children; idx < nc; ++idx, ++childP ) + if( tw->tabs.hilight == *childP ) + break ; + + switch( params[0][0] ) { + case 'u': /* up */ + case 'U': + if( idx == 0 ) + idx = nc ; + newhl = tw->composite.children[idx-1] ; + break ; + + case 'd': /* down */ + case 'D': + if( ++idx >= nc ) + idx = 0 ; + newhl = tw->composite.children[idx] ; + break ; + + case 'h': + case 'H': + newhl = tw->composite.children[0] ; + break ; + + case 'e': + case 'E': + newhl = tw->composite.children[nc-1] ; + break ; + } + } + + XawTabsSetHighlight(w, newhl) ; +} + + + +static void +TabsUnhighlight(Widget w, XEvent *event, String *params, Cardinal *num_params) +{ + TabsWidget tw = (TabsWidget) w ; + int nc = tw->composite.num_children ; + + if( nc <= 0 ) + return ; + + if( tw->tabs.hilight != NULL ) + DrawHighlight(tw, tw->tabs.hilight, True) ; +} + + + + + +/**************************************************************** + * + * Public Procedures + * + ****************************************************************/ + + + /* Set the top tab, optionally call all callbacks. */ +void +XawTabsSetTop(Widget w, Bool callCallbacks) +{ + TabsWidget tw = (TabsWidget)w->core.parent ; + TabsConstraints tab ; + Widget oldtop = tw->tabs.topWidget ; + + if( !XtIsSubclass(w->core.parent, tabsWidgetClass) ) + { + char line[1024] ; + sprintf(line, "XawTabsSetTop: widget \"%s\" is not the child of a tabs widget.", XtName(w)) ; + XtAppWarning(XtWidgetToApplicationContext(w), line) ; + return ; + } + + if( callCallbacks ) + XtCallCallbackList(w, tw->tabs.popdownCallbacks, + (XtPointer)tw->tabs.topWidget) ; + + if( !XtIsRealized(w) ) { + tw->tabs.topWidget = w ; + tw->tabs.needs_layout = True ; + return ; + } + + XRaiseWindow(XtDisplay(w), XtWindow(w)) ; +#ifdef NEED_MOTIF + XtVaSetValues(oldtop, XmNtraversalOn, False, 0) ; + XtVaSetValues(w, XmNtraversalOn, True, 0) ; +#endif + + tab = (TabsConstraints) w->core.constraints ; + if( tab->tabs.row == 0 ) + { + /* Easy case; undraw current top, undraw new top, assign new + * top, redraw all borders. + * We *could* just erase and execute a full redraw, but I like to + * reduce screen flicker. + */ + UndrawTab(tw, oldtop) ; /* undraw old */ + DrawBorder(tw, oldtop, True) ; + UndrawTab(tw, w) ; /* undraw new */ + DrawBorder(tw, w, True) ; + tw->tabs.topWidget = w ; + DrawTab(tw, oldtop, True) ; /* redraw old */ + DrawTab(tw, w, True) ; /* redraw new */ + DrawTabs(tw, False) ; + } + else + { + tw->tabs.topWidget = w ; + TabsShuffleRows(tw) ; + XClearWindow(XtDisplay((Widget)tw), XtWindow((Widget)tw)) ; + XtClass(tw)->core_class.expose((Widget)tw,NULL,None) ; + } + + XawTabsSetHighlight((Widget)tw, w) ; + + if( callCallbacks ) + XtCallCallbackList(w, tw->tabs.callbacks, (XtPointer)w) ; +} + + + /* Set the top tab, optionally call all callbacks. */ +void +XawTabsSetHighlight(Widget t, Widget w) +{ + TabsWidget tw = (TabsWidget)t ; + TabsConstraints tab ; + Widget oldtop = tw->tabs.topWidget ; + + if( !XtIsSubclass(t, tabsWidgetClass) ) + return ; + + if( XtIsRealized(t) && w != tw->tabs.hilight ) + { + if( tw->tabs.hilight != NULL ) + DrawHighlight(tw, tw->tabs.hilight, True) ; + if( w != NULL ) + DrawHighlight(tw, w, False) ; + } + + tw->tabs.hilight = w ; +} + + + + +/**************************************************************** + * + * Private Procedures + * + ****************************************************************/ + + +static void +TabsAllocGCs(TabsWidget tw) +{ + TabsAllocFgGC(tw) ; + TabsAllocGreyGC(tw) ; + tw->tabs.backgroundGC = AllocBackgroundGC((Widget)tw, None) ; + tw->tabs.topGC = AllocTopShadowGC((Widget)tw, + tw->tabs.top_shadow_contrast, tw->tabs.be_nice_to_cmap) ; + tw->tabs.botGC = AllocBotShadowGC((Widget)tw, + tw->tabs.bot_shadow_contrast, tw->tabs.be_nice_to_cmap) ; +} + + +static void +TabsFreeGCs(TabsWidget tw) +{ + Widget w = (Widget) tw; + + XtReleaseGC(w, tw->tabs.foregroundGC) ; + XtReleaseGC(w, tw->tabs.greyGC) ; + XtReleaseGC(w, tw->tabs.backgroundGC) ; + XtReleaseGC(w, tw->tabs.topGC) ; + XtReleaseGC(w, tw->tabs.botGC) ; +#ifdef HAVE_XMU + XmuReleaseStippledPixmap(XtScreen(w), tw->tabs.grey50) ; +#endif +} + + + + + + /* Redraw entire Tabs widget */ + +static void +DrawTabs(TabsWidget tw, Bool labels) +{ + Widget *childP ; + int i,j ; + Dimension s = SHADWID ; + Dimension th = tw->tabs.tab_height ; + Position y ; + TabsConstraints tab ; + + if( !XtIsRealized((Widget)tw)) + return ; + + /* draw tabs and frames by row except for the top tab, which + * is drawn last. (This is inefficiently written, but should not + * be too slow as long as there are not a lot of rows.) + */ + + y = tw->tabs.numRows == 1 ? TABDELTA : 0 ; + for(i=0; itabs.numRows; ++i, y += th) + { + for( j=tw->tabs.displayChildren, childP=tw->composite.children; + --j >= 0; ++childP ) + if( XtIsManaged(*childP) ) + { + tab = (TabsConstraints)(*childP)->core.constraints; + if( tab->tabs.row == i && *childP != tw->tabs.topWidget ) + DrawTab(tw, *childP, labels) ; + } + if( i != tw->tabs.numRows -1 ) + DrawTrim(tw, 0,y+th, tw->core.width, th+s, False,False) ; + } + + DrawFrame(tw) ; + + /* and now the top tab */ + if( tw->tabs.topWidget != NULL ) + DrawTab(tw, tw->tabs.topWidget, labels) ; +} + + + +/* Draw one tab. Corners are rounded very slightly. */ + +static void +DrawTab(TabsWidget tw, Widget child, Bool labels) +{ + GC gc ; + int x,y ; + + if( !XtIsRealized((Widget)tw)) + return ; + + DrawBorder(tw, child, False) ; + + if( labels ) + { + TabsConstraints tab = (TabsConstraints)child->core.constraints; + Display *dpy = XtDisplay((Widget)tw) ; + Window win = XtWindow((Widget)tw) ; + String lbl = tab->tabs.label != NULL ? + tab->tabs.label : XtName(child) ; + + if( XtIsSensitive(child) ) + { + gc = tw->tabs.foregroundGC ; + XSetForeground(dpy, gc, tab->tabs.foreground) ; + } + else + { + /* grey pixel allocation deferred until now */ + if( !tab->tabs.greyAlloc ) + { + if( tw->tabs.be_nice_to_cmap || tw->core.depth == 1 ) + tab->tabs.grey = tab->tabs.foreground ; + else + tab->tabs.grey = AllocGreyPixel((Widget)tw, + tab->tabs.foreground, + tw->core.background_pixel, + tw->tabs.insensitive_contrast ) ; + tab->tabs.greyAlloc = True ; + } + gc = tw->tabs.greyGC ; + XSetForeground(dpy, gc, tab->tabs.grey) ; + } + + x = tab->tabs.x ; + y = tab->tabs.y ; + if( child == tw->tabs.topWidget ) + y -= TABLDELTA ; + + if( tab->tabs.left_bitmap != None && tab->tabs.lbm_width > 0 ) + { + if( tab->tabs.lbm_depth == 1 ) + XCopyPlane(dpy, tab->tabs.left_bitmap, win,gc, + 0,0, tab->tabs.lbm_width, tab->tabs.lbm_height, + x+tab->tabs.lbm_x, y+tab->tabs.lbm_y, 1L) ; + else + XCopyArea(dpy, tab->tabs.left_bitmap, win,gc, + 0,0, tab->tabs.lbm_width, tab->tabs.lbm_height, + x+tab->tabs.lbm_x, y+tab->tabs.lbm_y) ; + } + + if( lbl != NULL && tw->tabs.font != NULL ) + XDrawString(dpy,win,gc, + x+tab->tabs.l_x, y+tab->tabs.l_y, + lbl, (int)strlen(lbl)) ; + } + + if( child == tw->tabs.hilight ) + DrawHighlight(tw, child, False) ; +} + + + /* draw frame all the way around the child windows. */ + +static void +DrawFrame(TabsWidget tw) +{ + GC topgc = tw->tabs.topGC ; + GC botgc = tw->tabs.botGC ; + Dimension s = SHADWID ; + Dimension ch = tw->tabs.child_height ; + Draw3dBox((Widget)tw, 0,tw->tabs.tab_total, + tw->core.width, ch+2*s, s, topgc, botgc) ; +} + + + /* draw trim around a tab or underneath a row of tabs */ + +static void +DrawTrim(TabsWidget tw, /* widget */ + int x, /* upper-left corner */ + int y, + int wid, /* total size */ + int hgt, + Bool bottom, /* draw bottom? */ + Bool undraw) /* undraw all */ +{ + Display *dpy = XtDisplay((Widget)tw) ; + Window win = XtWindow((Widget)tw) ; + GC bggc = tw->tabs.backgroundGC ; + GC topgc = undraw ? bggc : tw->tabs.topGC ; + GC botgc = undraw ? bggc : tw->tabs.botGC ; + if( bottom ) + XDrawLine(dpy,win,bggc, x,y+hgt-1, x+wid-1,y+hgt-1) ; /* bottom */ + XDrawLine(dpy,win,topgc, x,y+2, x,y+hgt-2) ; /* left */ + XDrawPoint(dpy,win,topgc, x+1,y+1) ; /* corner */ + XDrawLine(dpy,win,topgc, x+2,y, x+wid-3,y) ; /* top */ + XDrawLine(dpy,win,botgc, x+wid-2,y+1, x+wid-2,y+hgt-2) ; /* right */ + XDrawLine(dpy,win,botgc, x+wid-1,y+2, x+wid-1,y+hgt-2) ; /* right */ +} + + +/* Draw one tab border. */ + +static void +DrawBorder(TabsWidget tw, Widget child, Bool undraw) +{ + TabsConstraints tab = (TabsConstraints)child->core.constraints; + Position x = tab->tabs.x ; + Position y = tab->tabs.y ; + Dimension twid = tab->tabs.width ; + Dimension thgt = tw->tabs.tab_height ; + + /* top tab requires a little special attention; it overlaps + * neighboring tabs slightly, so the background must be cleared + * in the region of the overlap to partially erase those neighbors. + * TODO: is this worth doing with regions instead? + */ + if( child == tw->tabs.topWidget ) + { + Display *dpy = XtDisplay((Widget)tw) ; + Window win = XtWindow((Widget)tw) ; + GC bggc = tw->tabs.backgroundGC ; + XRectangle rects[3] ; + x -= TABDELTA ; + y -= TABDELTA ; + twid += TABDELTA*2 ; + thgt += TABDELTA ; + AddRect(0, x,y+1,twid,TABDELTA) ; + AddRect(1, x+1,y,TABDELTA,thgt) ; + AddRect(2, x+twid-TABDELTA-1,y,TABDELTA,thgt) ; + XFillRectangles(dpy,win,bggc, rects, 3) ; + } + + DrawTrim(tw, x,y,twid,thgt+1, child == tw->tabs.topWidget, undraw) ; +} + + +/* Draw highlight around tab that has focus */ + +static void +DrawHighlight(TabsWidget tw, Widget child, Bool undraw) +{ + TabsConstraints tab = (TabsConstraints)child->core.constraints; + Display *dpy = XtDisplay((Widget)tw) ; + Window win = XtWindow((Widget)tw) ; + GC gc ; + Position x = tab->tabs.x ; + Position y = tab->tabs.y ; + Dimension wid = tab->tabs.width ; + Dimension hgt = tw->tabs.tab_height ; + XPoint points[6] ; + + /* top tab does not have a highlight */ + + if( child == tw->tabs.topWidget ) + return ; + + if( undraw ) + gc = tw->tabs.backgroundGC ; + + else if( XtIsSensitive(child) ) + { + gc = tw->tabs.foregroundGC ; + XSetForeground(dpy, gc, tab->tabs.foreground) ; + } + else + { + gc = tw->tabs.greyGC ; + XSetForeground(dpy, gc, tab->tabs.grey) ; + } + + points[0].x = x+1 ; points[0].y = y+hgt-1 ; + points[1].x = x+1 ; points[1].y = y+2 ; + points[2].x = x+2 ; points[2].y = y+1 ; + points[3].x = x+wid-4 ; points[3].y = y+1 ; + points[4].x = x+wid-3 ; points[4].y = y+2 ; + points[5].x = x+wid-3 ; points[5].y = y+hgt-1 ; + + XDrawLines(dpy,win,gc, points,6, CoordModeOrigin) ; +} + + +/* Undraw one tab interior */ + +static void +UndrawTab(TabsWidget tw, Widget child) +{ + TabsConstraints tab = (TabsConstraints)child->core.constraints; + Position x = tab->tabs.x ; + Position y = tab->tabs.y ; + Dimension twid = tab->tabs.width ; + Dimension thgt = tw->tabs.tab_height ; + Display *dpy = XtDisplay((Widget)tw) ; + Window win = XtWindow((Widget)tw) ; + GC bggc = tw->tabs.backgroundGC ; + + XFillRectangle(dpy,win,bggc, x,y, twid,thgt) ; +} + + + + + + /* GEOMETRY UTILITIES */ + + + /* Compute the size of one child's tab. Positions will be computed + * elsewhere. + * + * height: font height + vertical_space*2 + shadowWid*2 + * width: string width + horizontal_space*2 + shadowWid*2 + * + * All tabs are the same height, so that is computed elsewhere. + */ + +static void +TabWidth(Widget w) +{ + TabsConstraints tab = (TabsConstraints) w->core.constraints ; + TabsWidget tw = (TabsWidget)XtParent(w) ; + String lbl = tab->tabs.label != NULL ? + tab->tabs.label : XtName(w) ; + XFontStruct *font = tw->tabs.font ; + int iw = tw->tabs.internalWidth ; + + tab->tabs.width = iw + SHADWID*2 ; + tab->tabs.l_x = tab->tabs.lbm_x = SHADWID + iw ; + + if( tab->tabs.left_bitmap != None ) + { + tab->tabs.width += tab->tabs.lbm_width + iw ; + tab->tabs.l_x += tab->tabs.lbm_width + iw ; + tab->tabs.lbm_y = (tw->tabs.tab_height - tab->tabs.lbm_height)/2 ; + } + + if( lbl != NULL && font != NULL ) + { + tab->tabs.width += XTextWidth( font, lbl, (int)strlen(lbl) ) + iw ; + tab->tabs.l_y = (tw->tabs.tab_height + + tw->tabs.font->max_bounds.ascent - + tw->tabs.font->max_bounds.descent)/2 ; + } +} + + + + /* Lay out tabs to fit in given width. Compute x,y position and + * row number for each tab. Return number of rows and total height + * required by all tabs. If there is only one row, add TABDELTA + * height to the total. Rows are assigned bottom to top. + * + * Tabs are indented from the edges by INDENT. + * + * TODO: if they require more than two rows and the total height:width + * ratio is more than 2:1, then try something else. + */ + +static int +TabLayout(TabsWidget tw, int wid, int hgt, Dimension *reply_height, Bool query_only) +{ + int i, row ; + int num_children = tw->composite.num_children ; + Widget *childP ; + Dimension w ; + Position x,y ; + TabsConstraints tab ; + + if (!query_only) + tw->tabs.displayChildren = 0; + + /* Algorithm: loop through children, assign X positions. If a tab + * would extend beyond the right edge, start a new row. After all + * rows are assigned, make a second pass and assign Y positions. + */ + + if( num_children > 0 ) + { + /* Loop through the tabs and see how much space they need. */ + + row = 0 ; + x = INDENT ; + y = 0 ; + wid -= INDENT ; + for(i=num_children, childP=tw->composite.children; --i >= 0; ++childP) + if( XtIsManaged(*childP) ) + { + tab = (TabsConstraints) (*childP)->core.constraints ; + w = tab->tabs.width ; + if( x + w > wid ) { /* new row */ + if (y + tw->tabs.tab_height > hgt) + break; + ++row ; + x = INDENT ; + y += tw->tabs.tab_height ; + } + if( !query_only ) { + tab->tabs.x = x ; + tab->tabs.y = y ; + tab->tabs.row = row ; + } + x += w + SPACING ; + if (!query_only) + tw->tabs.displayChildren++; + } + /* If there was only one row, increse the height by TABDELTA */ + if( ++row == 1 ) + { + y = TABDELTA ; + if( !query_only ) + for(i=num_children, childP=tw->composite.children; + --i >= 0 ; ++childP) + if( XtIsManaged(*childP) ) + { + tab = (TabsConstraints) (*childP)->core.constraints ; + tab->tabs.y = y ; + } + } + y += tw->tabs.tab_height ; + } + else + row = y = 0 ; + + if( !query_only ) { + tw->tabs.tab_total = y ; + tw->tabs.numRows = row ; + } + + if( reply_height != NULL ) + *reply_height = y ; + + return row ; +} + + + + /* Find max preferred child size. Returned sizes include child + * border widths. We only ever ask a child its preferred + * size once. After that, the preferred size is updated only + * if the child makes a geometry request. + */ + +static void +GetPreferredSizes(TabsWidget tw) +{ + int i ; + Widget *childP = tw->composite.children ; + XtWidgetGeometry preferred ; + TabsConstraints tab ; + Dimension cw = 0, ch = 0 ; + + for(i=tw->tabs.displayChildren; --i >= 0; ++childP) + if( XtIsManaged(*childP) ) + { + tab = (TabsConstraints) (*childP)->core.constraints ; + if( !tab->tabs.queried ) { + (void) XtQueryGeometry(*childP, NULL, &preferred) ; + tab->tabs.bwid = preferred.border_width ; + tab->tabs.wid = preferred.width + preferred.border_width * 2 ; + tab->tabs.hgt = preferred.height + preferred.border_width * 2 ; + tab->tabs.queried = True ; + } + cw = Max(cw, tab->tabs.wid ) ; + ch = Max(ch, tab->tabs.hgt ) ; + } + tw->tabs.max_cw = cw ; + tw->tabs.max_ch = ch ; +} + + + + /* Find max preferred child size. Returned sizes include child + * border widths. */ + +static void +MaxChild(TabsWidget tw) +{ + Dimension cw,ch ; /* child width, height */ + int i ; + Widget *childP = tw->composite.children ; + TabsConstraints tab ; + + cw = ch = 0 ; + + for(i=tw->composite.num_children; --i >=0; ++childP) + if( XtIsManaged(*childP) ) + { + tab = (TabsConstraints) (*childP)->core.constraints ; + cw = Max(cw, tab->tabs.wid ) ; + ch = Max(ch, tab->tabs.hgt ) ; + } + + tw->tabs.max_cw = cw ; + tw->tabs.max_ch = ch ; +} + + + + /* rotate row numbers to bring current widget to bottom row, + * compute y positions for all tabs + */ + +static void +TabsShuffleRows(TabsWidget tw) +{ + TabsConstraints tab ; + int move ; + int nrows ; + Widget *childP ; + Dimension th = tw->tabs.tab_height ; + Position bottom ; + int i ; + + /* There must be a top widget. If not, assign one. */ + if( tw->tabs.topWidget == NULL && tw->composite.children != NULL ) + for(i=tw->composite.num_children, childP=tw->composite.children; + --i >= 0; + ++childP) + if( XtIsManaged(*childP) ) { + tw->tabs.topWidget = *childP ; + break ; + } + + if( tw->tabs.topWidget != NULL ) + { + nrows = tw->tabs.numRows ; + assert( nrows > 0 ) ; + + if( nrows > 1 ) + { + tab = (TabsConstraints) tw->tabs.topWidget->core.constraints ; + assert( tab != NULL ) ; + + /* how far to move top row */ + move = nrows - tab->tabs.row ; + bottom = tw->tabs.tab_total - th ; + + for(i=tw->tabs.displayChildren, childP=tw->composite.children; + --i >= 0; + ++childP) + if( XtIsManaged(*childP) ) + { + tab = (TabsConstraints) (*childP)->core.constraints ; + tab->tabs.row = (tab->tabs.row + move) % nrows ; + tab->tabs.y = bottom - tab->tabs.row * th ; + } + } + } +} + + + /* find preferred size. Ask children, find size of largest, + * add room for tabs & return. This can get a little involved, + * as we don't want to have too many rows of tabs; we may widen + * the widget to reduce # of rows. + */ + +static int +PreferredSize( + TabsWidget tw, + Dimension *reply_width, /* total widget size */ + Dimension *reply_height, + Dimension *reply_cw, /* child widget size */ + Dimension *reply_ch) +{ + Dimension cw,ch ; /* child width, height */ + Dimension wid,hgt ; + Dimension rwid,rhgt ; + int nrow ; + + + /* find max desired child height */ +#ifdef COMMENT + MaxChild(tw, &cw, &ch) ; +#endif /* COMMENT */ + + wid = cw = tw->tabs.max_cw ; + hgt = ch = tw->tabs.max_ch ; + + nrow = PreferredSize2(tw, wid,hgt, &rwid, &rhgt) ; + + /* Check for absurd results (more than 2 rows, high aspect + * ratio). Try wider size if needed. + * TODO: make sure this terminates. + */ + + if( nrow > 2 && rhgt > rwid ) + { + Dimension w0, w1 ; + + /* step 1: start doubling size until it's too big */ + do { + w0 = wid ; + wid = Max(wid*2, wid+20) ; + nrow = PreferredSize2(tw, wid,hgt, &rwid,&rhgt) ; + } while( nrow > 2 && rhgt > rwid ) ; + w1 = wid ; + + /* step 2: use Newton's method to find ideal size. Stop within + * 8 pixels. + */ + while( w1 > w0 + 8 ) + { + wid = (w0+w1)/2 ; + nrow = PreferredSize2(tw, wid,hgt, &rwid,&rhgt) ; + if( nrow > 2 && rhgt > rwid ) + w0 = wid ; + else + w1 = wid ; + } + wid = w1 ; + } + + *reply_width = rwid ; + *reply_height = rhgt ; + if( reply_cw != NULL ) *reply_cw = cw ; + if( reply_ch != NULL ) *reply_ch = ch ; + return nrow ; +} + + + /* Find preferred size, given size of children. */ + +static int +PreferredSize2( + TabsWidget tw, + int cw, /* child width, height */ + int ch, + Dimension *reply_width, /* total widget size */ + Dimension *reply_height) +{ + Dimension s = SHADWID ; + + /* make room for shadow frame */ + cw += s*2 ; + ch += s*2 ; + + return PreferredSize3(tw, cw, ch, reply_width, reply_height) ; +} + + + /* Find preferred size, given size of children+shadow. */ + +static int +PreferredSize3( + TabsWidget tw, + int wid, /* child width, height */ + int hgt, + Dimension *reply_width, /* total widget size */ + Dimension *reply_height) +{ + Dimension th ; /* space used by tabs */ + int nrows ; + + if( tw->composite.num_children > 0 ) + nrows = TabLayout(tw, wid, hgt, &th, True) ; + else { + th = 0 ; + nrows = 0 ; + } + + *reply_width = Max(wid, MIN_WID) ; + *reply_height = Max(th+hgt, MIN_HGT) ; + + return nrows ; +} + + +static void +MakeSizeRequest(TabsWidget tw) +{ + Widget w = (Widget)tw ; + XtWidgetGeometry request, reply ; + XtGeometryResult result ; + Dimension cw,ch ; + + request.request_mode = CWWidth | CWHeight ; + PreferredSize(tw, &request.width, &request.height, &cw, &ch) ; + + if( request.width == tw->core.width && + request.height == tw->core.height ) + return ; + + result = XtMakeGeometryRequest(w, &request, &reply) ; + + if( result == XtGeometryAlmost ) + { + /* Bugger. Didn't get what we want, but were offered a + * compromise. If the width was too small, recompute + * based on the too-small width and try again. + * If the height was too small, make a wild-ass guess + * at a wider width and try again. + */ + + if( reply.width < request.width && reply.height >= request.height ) + { + Dimension s = SHADWID ; + ch += s*2 ; + PreferredSize3(tw, reply.width,ch, &request.width, &request.height); + result = XtMakeGeometryRequest(w, &request, &reply) ; + if( result == XtGeometryAlmost ) + (void) XtMakeGeometryRequest(w, &reply, NULL) ; + } + + else + (void) XtMakeGeometryRequest(w, &reply, NULL) ; + } +} + + +static void +getBitmapInfo(TabsWidget tw, TabsConstraints tab) +{ + Window root ; + int x,y ; + unsigned int bw ; + + if( tab->tabs.left_bitmap == None || + !XGetGeometry(XtDisplay(tw), tab->tabs.left_bitmap, &root, &x, &y, + &tab->tabs.lbm_width, &tab->tabs.lbm_height, + &bw, &tab->tabs.lbm_depth) ) + tab->tabs.lbm_width = tab->tabs.lbm_height = 0 ; +} + + + + + /* Code copied & modified from Gcs.c. This version has dynamic + * foreground. + */ + +static void +TabsAllocFgGC(TabsWidget tw) +{ + Widget w = (Widget) tw; + XGCValues values ; + + values.background = tw->core.background_pixel ; + values.font = tw->tabs.font->fid ; + values.line_style = LineOnOffDash ; + values.line_style = LineSolid ; + + tw->tabs.foregroundGC = + XtAllocateGC(w, w->core.depth, + GCBackground|GCFont|GCLineStyle, &values, + GCForeground, + GCSubwindowMode|GCGraphicsExposures|GCDashOffset| + GCDashList|GCArcMode) ; +} + +static void +TabsAllocGreyGC(TabsWidget tw) +{ + Widget w = (Widget) tw; + XGCValues values ; + + values.background = tw->core.background_pixel ; + values.font = tw->tabs.font->fid ; +#ifdef HAVE_XMU + if( tw->tabs.be_nice_to_cmap || w->core.depth == 1) + { + values.fill_style = FillStippled ; + tw->tabs.grey50 = + values.stipple = XmuCreateStippledPixmap(XtScreen(w), 1L, 0L, 1) ; + + tw->tabs.greyGC = + XtAllocateGC(w, w->core.depth, + GCBackground|GCFont|GCStipple|GCFillStyle, &values, + GCForeground, + GCSubwindowMode|GCGraphicsExposures|GCDashOffset| + GCDashList|GCArcMode) ; + } + else +#endif + { + tw->tabs.greyGC = + XtAllocateGC(w, w->core.depth, + GCFont, &values, + GCForeground, + GCBackground|GCSubwindowMode|GCGraphicsExposures|GCDashOffset| + GCDashList|GCArcMode) ; + } +} diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwtabs.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwtabs.h Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,205 @@ +/* Tabs Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + + This file is part of XEmacs. + + XEmacs is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 2, or (at your option) any + later version. + + XEmacs is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with XEmacs; see the file COPYING. If not, write to + the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + +/* + * This widget manages one or more child widgets, exactly one of which is + * visible. Above the child widgets is a graphic that looks like index + * tabs from file folders. Each tab corresponds to one of the child widgets. + * By clicking on a tab, the user can bring the corresponding widget to + * the top of the stack. + */ + + +#ifndef _Tabs_h +#define _Tabs_h + +#include + + +/*********************************************************************** + * + * Tabs Widget (subclass of CompositeClass) + * + ***********************************************************************/ + +/* Parameters: + + Name Class RepType Default Value + ---- ----- ------- ------------- + font Font XFontStruct* XtDefaultFont + internalWidth Width Dimension 4 *1 + internalHeight Height Dimension 2 *1 + topWidget TopWidget Widget *2 + callback Callback XtCallbackList NULL *3 + popdownCallback Callback XtCallbackList NULL *4 + selectInsensitive SelectInsensitive Boolean True *5 + beNiceToColormap BeNiceToColormap Boolean False *6 + topShadowContrast TopShadowContrast int 20 + bottomShadowContrast BottomShadowContrast int 40 + insensitiveContrast InsensitiveContrast int 33 *7 + + background Background Pixel XtDefaultBackground + border BorderColor Pixel XtDefaultForeground + borderWidth BorderWidth Dimension 1 + destroyCallback Callback Pointer NULL + hSpace HSpace Dimension 4 + height Height Dimension 0 + mappedWhenManaged MappedWhenManaged Boolean True + orientation Orientation XtOrientation vertical + vSpace VSpace Dimension 4 + width Width Dimension 0 + x Position Position 0 + y Position Position 0 + + Notes: + + 1 internalWidth, internalHeight specify the margins around the text + in the tabs. + 2 topWidget identifies the widget which is currently visible. + 3 callbacks are called whenever the user selects a tab. Call_data is + the new top widget. + 4 popdownCallbacks are called whenever the user selects a tab. Call_data is + the old (no longer visible) top widget. Note that popdownCallbacks + are called before callbacks. + 5 SelectInsensitive determines whether or not insensitive children may + be selected anyway. + 6 BeNiceToColormap causes the Tabs widget to use fewer colors. + 7 InsensitiveContrast sets the contrast used for labels of insensitive widgets. + +*/ + +/* Constraint parameters: + Name Class RepType Default Value + ---- ----- ------- ------------- + tabLabel Label String widget name + tabLeftBitmap LeftBitmap Pixmap None + tabForeground Foreground Pixel XtDefaultForeground + resizable Resizable Boolean False +*/ + +/* New fields */ + +#ifndef XtNtabLabel +#define XtNtabLabel "tabLabel" +#define XtNtabForeground "tabForeground" +#endif + +#ifndef XtNtabLeftBitmap +#define XtNtabLeftBitmap "tabLeftBitmap" +#endif + +#ifndef XtCLeftBitmap +#define XtCLeftBitmap "LeftBitmap" +#endif + +#ifndef XtCResizable +#define XtCResizable "Resizable" +#endif + +#ifndef XtNselectInsensitive +#define XtNselectInsensitive "selectInsensitive" +#define XtCSelectInsensitive "SelectInsensitive" +#endif + +#ifndef XtNnlabels +#define XtNnlabels "nlabels" +#define XtCNLabels "NLabels" +#endif +#ifndef XtNlabels +#define XtNlabels "labels" +#define XtCLabels "Labels" +#endif + +#ifndef XtNtopWidget +#define XtNtopWidget "topWidget" +#define XtCTopWidget "TopWidget" +#endif + +#ifndef XtNhSpace +#define XtNhSpace "hSpace" +#define XtCHSpace "HSpace" +#define XtNvSpace "vSpace" +#define XtCVSpace "VSpace" +#endif + +#ifndef XtNresizable +#define XtNresizable "resizable" +#endif + +#ifndef XtNinsensitiveContrast +#define XtNinsensitiveContrast "insensitiveContrast" +#define XtCInsensitiveContrast "InsensitiveContrast" +#endif + +#ifndef XtNshadowWidth +#define XtNshadowWidth "shadowWidth" +#define XtCShadowWidth "ShadowWidth" +#define XtNtopShadowPixel "topShadowPixel" +#define XtCTopShadowPixel "TopShadowPixel" +#define XtNbottomShadowPixel "bottomShadowPixel" +#define XtCBottomShadowPixel "BottomShadowPixel" +#define XtNtopShadowContrast "topShadowContrast" +#define XtCTopShadowContrast "TopShadowContrast" +#define XtNbottomShadowContrast "bottomShadowContrast" +#define XtCBottomShadowContrast "BottomShadowContrast" +#endif + +#ifndef XtNtopShadowPixmap +#define XtNtopShadowPixmap "topShadowPixmap" +#define XtCTopShadowPixmap "TopShadowPixmap" +#define XtNbottomShadowPixmap "bottomShadowPixmap" +#define XtCBottomShadowPixmap "BottomShadowPixmap" +#endif + +#ifndef XtNbeNiceToColormap +#define XtNbeNiceToColormap "beNiceToColormap" +#define XtCBeNiceToColormap "BeNiceToColormap" +#define XtNbeNiceToColourmap "beNiceToColormap" +#define XtCBeNiceToColourmap "BeNiceToColormap" +#endif + +/* Class record constants */ + +extern WidgetClass tabsWidgetClass; + +typedef struct _TabsClassRec *TabsWidgetClass; +typedef struct _TabsRec *TabsWidget; + +_XFUNCPROTOBEGIN + +extern void +XawTabsSetTop( +#if NeedFunctionPrototypes + Widget w, + Bool callCallbacks +#endif +) ; + +extern void +XawTabsSetHighlight( +#if NeedFunctionPrototypes + Widget tabs, + Widget w +#endif +) ; + +_XFUNCPROTOEND + +#endif /* _Tabs_h */ diff -r 28d9c139be4c -r 11054d720c21 lwlib/xlwtabsP.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lwlib/xlwtabsP.h Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,151 @@ +/* Tabs Widget for XEmacs. + Copyright (C) 1999 Edward A. Falk + +This file is part of XEmacs. + +XEmacs is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 2, or (at your option) any +later version. + +XEmacs is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with XEmacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 59 Temple Place - Suite 330, +Boston, MA 02111-1307, USA. */ + +/* Synched up with: TabsP.h 1.7 */ + +/* + * TabsP.h - Private definitions for Index Tabs widget + */ + +#ifndef _TabsP_h +#define _TabsP_h + +/*********************************************************************** + * + * Tabs Widget Private Data + * + ***********************************************************************/ + +#include + +#ifdef NEED_MOTIF +#include +#include +#endif + +#include "xlwtabs.h" + +/* New fields for the Tabs widget class record */ +typedef struct {XtPointer extension;} TabsClassPart; + +/* Full class record declaration */ +typedef struct _TabsClassRec { + CoreClassPart core_class; + CompositeClassPart composite_class; + ConstraintClassPart constraint_class; +#ifdef NEED_MOTIF + XmManagerClassPart manager_class; +#endif + TabsClassPart tabs_class; +} TabsClassRec; + +extern TabsClassRec tabsClassRec; + + + +/**************************************************************** + * + * instance record declaration + * + ****************************************************************/ + +/* New fields for the Tabs widget record */ +typedef struct { + /* resources */ + XFontStruct *font ; + Dimension internalHeight, internalWidth ; + Widget topWidget ; + XtCallbackList callbacks ; + XtCallbackList popdownCallbacks ; + Boolean selectInsensitive ; + Boolean be_nice_to_cmap ; + int top_shadow_contrast ; + int bot_shadow_contrast ; + int insensitive_contrast ; + + /* private state */ + Widget hilight ; + GC foregroundGC ; + GC backgroundGC ; + GC greyGC ; + GC topGC ; + GC botGC ; + Dimension tab_height ; /* height of tabs (all the same) */ + /* Note: includes top shadow only */ + Dimension tab_total ; /* total height of all tabs */ + Dimension child_width, child_height; /* child size, including borders */ + Dimension max_cw, max_ch ; /* max child preferred size */ + Cardinal numRows ; + Cardinal displayChildren ; + XtGeometryMask last_query_mode; + Boolean needs_layout ; + Pixmap grey50 ; /* TODO: cache this elsewhere */ +} TabsPart; + + +typedef struct _TabsRec { + CorePart core; + CompositePart composite; + ConstraintPart constraint; +#ifdef NEED_MOTIF + XmManagerPart manager; +#endif + TabsPart tabs; +} TabsRec; + + + + +/**************************************************************** + * + * constraint record declaration + * + ****************************************************************/ + +typedef struct _TabsConstraintsPart { + /* resources */ + String label ; + Pixmap left_bitmap ; + Pixel foreground ; + Boolean resizable ; + + /* private state */ + Pixel grey ; + Boolean greyAlloc ; + Dimension width ; /* tab width */ + Position x,y ; /* tab base position */ + short row ; /* tab row */ + Dimension wid,hgt ; /* desired size */ + Dimension bwid ; /* desired border width */ + Boolean queried ; /* we've asked child it's pref. size */ + Position l_x, l_y ; /* label position */ + Position lbm_x, lbm_y ; /* bitmap position */ + unsigned int lbm_width, lbm_height, lbm_depth ; +} TabsConstraintsPart ; + +typedef struct _TabsConstraintsRec { +#ifdef NEED_MOTIF + XmManagerConstraintPart manager; +#endif + TabsConstraintsPart tabs ; +} TabsConstraintsRec, *TabsConstraints ; + + +#endif /* _TabsP_h */ diff -r 28d9c139be4c -r 11054d720c21 man/ChangeLog --- a/man/ChangeLog Mon Aug 13 11:25:03 2007 +0200 +++ b/man/ChangeLog Mon Aug 13 11:26:11 2007 +0200 @@ -1,3 +1,43 @@ +1999-11-10 XEmacs Build Bot + + * XEmacs 21.2.20 is released + +1999-08-30 Robert Pluim + + * xemacs/packages.texi (Using Packages): Added description of + package-get-package-provider. + +1999-07-27 Charles G Waldman + + * xemacs-faq.texi (Q5.0.6): Describe `shell-multiple-shells' + +1999-08-01 Adrian Aichner + + * xemacs/programs.texi (Balanced Editing): Remove broken + line-break. + + * xemacs-faq.texi (Q1.0.6): Provide correct location in XEmacs + menus. + (Q1.4.1): ditto. + (Q1.4.3): ditto. + (Q2.0.5): Hyphenate words. + + * info.texi (Add): Fix one typo. + +1999-08-23 Stephane Epardaud + + * internals/internals.texi (Garbage Collection - Step by Step): + just added some dots to shut up compile warnings. + +1999-08-19 Matthias Neubauer + + * internals/internals.texi (Garbage Collection - Step by Step): + new section in chapter Allocation of Objects in XEmacs Lisp. + +1999-07-28 Andy Piper + + * internals.texi (Glyphs): add some glyph documentation. + 1999-07-30 XEmacs Build Bot * XEmacs 21.2.19 is released diff -r 28d9c139be4c -r 11054d720c21 man/info.texi --- a/man/info.texi Mon Aug 13 11:25:03 2007 +0200 +++ b/man/info.texi Mon Aug 13 11:26:11 2007 +0200 @@ -3,7 +3,7 @@ @setfilename ../info/info.info @settitle Info 1.0 @comment %**end of header -@comment $Id: info.texi,v 1.4 1998/06/30 06:35:28 steve Exp $ +@comment $Id: info.texi,v 1.4.2.1 1999/09/26 19:46:47 olivierg Exp $ @dircategory Texinfo documentation system @direntry @@ -681,7 +681,7 @@ Usually, the way to create the nodes is with Texinfo @pxref{Top,, Overview of Texinfo, texinfo, Texinfo: The GNU Documentation Format}); this has the advantage that you can also make a printed manual from them. However, -if hyou want to edit an Info file, here is how. +if you want to edit an Info file, here is how. The new node can live in an existing documentation file, or in a new one. It must have a @key{^_} character before it (invisible to the diff -r 28d9c139be4c -r 11054d720c21 man/internals/internals.texi --- a/man/internals/internals.texi Mon Aug 13 11:25:03 2007 +0200 +++ b/man/internals/internals.texi Mon Aug 13 11:26:11 2007 +0200 @@ -63,11 +63,12 @@ @titlepage @title XEmacs Internals Manual -@subtitle Version 1.2, October 1998 +@subtitle Version 1.3, August 1999 @author Ben Wing @author Martin Buchholz @author Hrvoje Niksic +@author Matthias Neubauer @page @vskip 0pt plus 1fill @@ -78,8 +79,8 @@ Copyright @copyright{} 1994, 1995 Board of Trustees, University of Illinois. @sp 2 -Version 1.2 @* -October 1998.@* +Version 1.3 @* +August 1999.@* Permission is granted to make and distribute verbatim copies of this manual provided the copyright notice and this permission notice are @@ -127,7 +128,8 @@ * Consoles; Devices; Frames; Windows:: * The Redisplay Mechanism:: * Extents:: -* Faces and Glyphs:: +* Faces:: +* Glyphs:: * Specifiers:: * Menus:: * Subprocesses:: @@ -174,6 +176,7 @@ * Introduction to Allocation:: * Garbage Collection:: * GCPROing:: +* Garbage Collection - Step by Step:: * Integers and Characters:: * Allocation from Frob Blocks:: * lrecords:: @@ -260,7 +263,9 @@ * Mathematics of Extent Ordering:: A rigorous foundation. * Extent Fragments:: Cached information useful for redisplay. -Faces and Glyphs +Faces + +Glyphs Specifiers @@ -4370,6 +4375,7 @@ * Introduction to Allocation:: * Garbage Collection:: * GCPROing:: +* Garbage Collection - Step by Step:: * Integers and Characters:: * Allocation from Frob Blocks:: * lrecords:: @@ -4714,6 +4720,502 @@ it obviates the need for @code{GCPRO}ing, and allows garbage collection to happen at any point at all, such as during object allocation. +@node Garbage Collection - Step by Step +@section Garbage Collection - Step by Step +@cindex garbage collection step by step + +@menu +* Invocation:: +* garbage_collect_1:: +* mark_object:: +* gc_sweep:: +* sweep_lcrecords_1:: +* compact_string_chars:: +* sweep_strings:: +* sweep_bit_vectors_1:: +@end menu + +@node Invocation +@subsection Invocation +@cindex garbage collection, invocation + +The first thing that anyone should know about garbage collection is: +when and how the garbage collector is invoked. One might think that this +could happen every time new memory is allocated, e.g. new objects are +created, but this is @emph{not} the case. Instead, we have the following +situation: + +The entry point of any process of garbage collection is an invocation +of the function @code{garbage_collect_1} in file @code{alloc.c}. The +invocation can occur @emph{explicitly} by calling the function +@code{Fgarbage_collect} (in addition this function provides information +about the freed memory), or can occur @emph{implicitly} in four different +situations: +@enumerate +@item +In function @code{main_1} in file @code{emacs.c}. This function is called +at each startup of xemacs. The garbage collection is invoked after all +initial creations are completed, but only if a special internal error +checking-constant @code{ERROR_CHECK_GC} is defined. +@item +In function @code{disksave_object_finalization} in file +@code{alloc.c}. The only purpose of this function is to clear the +objects from memory which need not be stored with xemacs when we dump out +an executable. This is only done by @code{Fdump_emacs} or by +@code{Fdump_emacs_data} respectively (both in @code{emacs.c}). The +actual clearing is accomplished by making these objects unreachable and +starting a garbage collection. The function is only used while building +xemacs. +@item +In function @code{Feval / eval} in file @code{eval.c}. Each time the +well known and often used function eval is called to evaluate a form, +one of the first things that could happen, is a potential call of +@code{garbage_collect_1}. There exist three global variables, +@code{consing_since_gc} (counts the created cons-cells since the last +garbage collection), @code{gc_cons_threshold} (a specified threshold +after which a garbage collection occurs) and @code{always_gc}. If +@code{always_gc} is set or if the threshold is exceeded, the garbage +collection will start. +@item +In function @code{Ffuncall / funcall} in file @code{eval.c}. This +function evaluates calls of elisp functions and works according to +@code{Feval}. +@end enumerate + +The upshot is that garbage collection can basically occur everywhere +@code{Feval}, respectively @code{Ffuncall}, is used - either directly or +through another function. Since calls to these two functions are +hidden in various other functions, many calls to +@code{garabge_collect_1} are not obviously foreseeable, and therefore +unexpected. Instances where they are used that are worth remembering are +various elisp commands, as for example @code{or}, +@code{and}, @code{if}, @code{cond}, @code{while}, @code{setq}, etc., +miscellaneous @code{gui_item_...} functions, everything related to +@code{eval} (@code{Feval_buffer}, @code{call0}, ...) and inside +@code{Fsignal}. The latter is used to handle signals, as for example the +ones raised by every @code{QUITE}-macro triggered after pressing Ctrl-g. + +@node garbage_collect_1 +@subsection @code{garbage_collect_1} +@cindex @code{garbage_collect_1} + +We can now describe exactly what happens after the invocation takes +place. +@enumerate +@item +There are several cases in which the garbage collector is left immediately: +when we are already garbage collecting (@code{gc_in_progress}), when +the garbage collection is somehow forbidden +(@code{gc_currently_forbidden}), when we are currently displaying something +(@code{in_display}) or when we are preparing for the armageddon of the +whole system (@code{preparing_for_armageddon}). +@item +Next the correct frame in which to put +all the output occurring during garbage collecting is determined. In +order to be able to restore the old display's state after displaying the +message, some data about the current cursor position has to be +saved. The variables @code{pre_gc_curser} and @code{cursor_changed} take +care of that. +@item +The state of @code{gc_currently_forbidden} must be restored after +the garbage collection, no matter what happens during the process. We +accomplish this by @code{record_unwind_protect}ing the suitable function +@code{restore_gc_inhibit} together with the current value of +@code{gc_currently_forbidden}. +@item +If we are concurrently running an interactive xemacs session, the next step +is simply to show the garbage collector's cursor/message. +@item +The following steps are the intrinsic steps of the garbage collector, +therefore @code{gc_in_progress} is set. +@item +For debugging purposes, it is possible to copy the current C stack +frame. However, this seems to be a currently unused feature. +@item +Before actually starting to go over all live objects, references to +objects that are no longer used are pruned. We only have to do this for events +(@code{clear_event_resource}) and for specifiers +(@code{cleanup_specifiers}). +@item +Now the mark phase begins and marks all accessible elements. In order to +start from +all slots that serve as roots of accessibility, the function +@code{mark_object} is called for each root individually to go out from +there to mark all reachable objects. All roots that are traversed are +shown in their processed order: +@itemize @bullet +@item +all constant symbols and static variables that are registered via +@code{staticpro}@ in the array @code{staticvec}. +@xref{Adding Global Lisp Variables}. +@item +all Lisp objects that are created in C functions and that must be +protected from freeing them. They are registered in the global +list @code{gcprolist}. +@xref{GCPROing}. +@item +all local variables (i.e. their name fields @code{symbol} and old +values @code{old_values}) that are bound during the evaluation by the Lisp +engine. They are stored in @code{specbinding} structs pushed on a stack +called @code{specpdl}. +@xref{Dynamic Binding; The specbinding Stack; Unwind-Protects}. +@item +all catch blocks that the Lisp engine encounters during the evaluation +cause the creation of structs @code{catchtag} inserted in the list +@code{catchlist}. Their tag (@code{tag}) and value (@code{val} fields +are freshly created objects and therefore have to be marked. +@xref{Catch and Throw}. +@item +every function application pushes new structs @code{backtrace} +on the call stack of the Lisp engine (@code{backtrace_list}). The unique +parts that have to be marked are the fields for each function +(@code{function}) and all their arguments (@code{args}). +@xref{Evaluation}. +@item +all objects that are used by the redisplay engine that must not be freed +are marked by a special function called @code{mark_redisplay} (in +@code{redisplay.c}). +@item +all objects created for profiling purposes are allocated by C functions +instead of using the lisp allocation mechanisms. In order to receive the +right ones during the sweep phase, they also have to be marked +manually. That is done by the function @code{mark_profiling_info} +@end itemize +@item +Hash tables in Xemacs belong to a kind of special objects that +make use of a concept often called 'weak pointers'. +To make a long story short, these kind of pointers are not followed +during the estimation of the live objects during garbage collection. +Any object referenced only by weak pointers is collected +anyway, and the reference to it is cleared. In hash tables there are +different usage patterns of them, manifesting in different types of hash +tables, namely 'non-weak', 'weak', 'key-weak' and 'value-weak' +(internally also 'key-car-weak' and 'value-car-weak') hash tables, each +clearing entries depending on different conditions. More information can +be found in the documentation to the function @code{make-hash-table}. + +Because there are complicated dependency rules about when and what to +mark while processing weak hash tables, the standard @code{marker} +method is only active if it is marking non-weak hash tables. As soon as +a weak component is in the table, the hash table entries are ignored +while marking. Instead their marking is done each separately by the +function @code{finish_marking_weak_hash_tables}. This function iterates +over each hash table entry @code{hentries} for each weak hash table in +@code{Vall_weak_hash_tables}. Depending on the type of a table, the +appropriate action is performed. +If a table is acting as @code{HASH_TABLE_KEY_WEAK}, and a key already marked, +everything reachable from the @code{value} component is marked. If it is +acting as a @code{HASH_TABLE_VALUE_WEAK} and the value component is +already marked, the marking starts beginning only from the +@code{key} component. +If it is a @code{HASH_TABLE_KEY_CAR_WEAK} and the car +of the key entry is already marked, we mark both the @code{key} and +@code{value} components. +Finally, if the table is of the type @code{HASH_TABLE_VALUE_CAR_WEAK} +and the car of the value components is already marked, again both the +@code{key} and the @code{value} components get marked. + +Again, there are lists with comparable properties called weak +lists. There exist different peculiarities of their types called +@code{simple}, @code{assoc}, @code{key-assoc} and +@code{value-assoc}. You can find further details about them in the +description to the function @code{make-weak-list}. The scheme of their +marking is similar: all weak lists are listed in @code{Qall_weak_lists}, +therefore we iterate over them. The marking is advanced until we hit an +already marked pair. Then we know that during a former run all +the rest has been marked completely. Again, depending on the special +type of the weak list, our jobs differ. If it is a @code{WEAK_LIST_SIMPLE} +and the elem is marked, we mark the @code{cons} part. If it is a +@code{WEAK_LIST_ASSOC} and not a pair or a pair with both marked car and +cdr, we mark the @code{cons} and the @code{elem}. If it is a +@code{WEAK_LIST_KEY_ASSOC} and not a pair or a pair with a marked car of +the elem, we mark the @code{cons} and the @code{elem}. Finally, if it is +a @code{WEAK_LIST_VALUE_ASSOC} and not a pair or a pair with a marked +cdr of the elem, we mark both the @code{cons} and the @code{elem}. + +Since, by marking objects in reach from weak hash tables and weak lists, +other objects could get marked, this perhaps implies further marking of +other weak objects, both finishing functions are redone as long as +yet unmarked objects get freshly marked. + +@item +After completing the special marking for the weak hash tables and for the weak +lists, all entries that point to objects that are going to be swept in +the further process are useless, and therefore have to be removed from +the table or the list. + +The function @code{prune_weak_hash_tables} does the job for weak hash +tables. Totally unmarked hash tables are removed from the list +@code{Vall_weak_hash_tables}. The other ones are treated more carefully +by scanning over all entries and removing one as soon as one of +the components @code{key} and @code{value} is unmarked. + +The same idea applies to the weak lists. It is accomplished by +@code{prune_weak_lists}: An unmarked list is pruned from +@code{Vall_weak_lists} immediately. A marked list is treated more +carefully by going over it and removing just the unmarked pairs. + +@item +The function @code{prune_specifiers} checks all listed specifiers held +in @code{Vall_speficiers} and removes the ones from the lists that are +unmarked. + +@item +All syntax tables are stored in a list called +@code{Vall_syntax_tables}. The function @code{prune_syntax_tables} walks +through it and unlinks the tables that are unmarked. + +@item +Next, we will attack the complete sweeping - the function +@code{gc_sweep} which holds the predominance. +@item +First, all the variables with respect to garbage collection are +reset. @code{consing_since_gc} - the counter of the created cells since +the last garbage collection - is set back to 0, and +@code{gc_in_progress} is not @code{true} anymore. +@item +In case the session is interactive, the displayed cursor and message are +removed again. +@item +The state of @code{gc_inhibit} is restored to the former value by +unwinding the stack. +@item +A small memory reserve is always held back that can be reached by +@code{breathing_space}. If nothing more is left, we create a new reserve +and exit. +@end enumerate + +@node mark_object +@subsection @code{mark_object} +@cindex @code{mark_object} + +The first thing that is checked while marking an object is whether the +object is a real Lisp object @code{Lisp_Type_Record} or just an integer +or a character. Integers and characters are the only two types that are +stored directly - without another level of indirection, and therefore they +don´t have to be marked and collected. +@xref{How Lisp Objects Are Represented in C}. + +The second case is the one we have to handle. It is the one when we are +dealing with a pointer to a Lisp object. But, there exist also three +possibilities, that prevent us from doing anything while marking: The +object is read only which prevents it from being garbage collected, +i.e. marked (@code{C_READONLY_RECORD_HEADER}). The object in question is +already marked, and need not be marked for the second time (checked by +@code{MARKED_RECORD_HEADER_P}). If it is a special, unmarkable object +(@code{UNMARKABLE_RECORD_HEADER_P}, apparently, these are objects that +sit in some CONST space, and can therefore not be marked, see +@code{this_one_is_unmarkable} in @code{alloc.c}). + +Now, the actual marking is feasible. We do so by once using the macro +@code{MARK_RECORD_HEADER} to mark the object itself (actually the +special flag in the lrecord header), and calling its special marker +"method" @code{marker} if available. The marker method marks every +other object that is in reach from our current object. Note, that these +marker methods should not call @code{mark_object} recursively, but +instead should return the next object from where further marking has to +be performed. + +In case another object was returned, as mentioned before, we reiterate +the whole @code{mark_object} process beginning with this next object. + +@node gc_sweep +@subsection @code{gc_sweep} +@cindex @code{gc_sweep} + +The job of this function is to free all unmarked records from memory. As +we know, there are different types of objects implemented and managed, and +consequently different ways to free them from memory. +@xref{Introduction to Allocation}. + +We start with all objects stored through @code{lcrecords}. All +bulkier objects are allocated and handled using that scheme of +@code{lcrecords}. Each object is @code{malloc}ed separately +instead of placing it in one of the contiguous frob blocks. All types +that are currently stored +using @code{lcrecords}´s @code{alloc_lcrecord} and +@code{make_lcrecord_list} are the types: vectors, buffers, +char-table, char-table-entry, console, weak-list, database, device, +ldap, hash-table, command-builder, extent-auxiliary, extent-info, face, +coding-system, frame, image-instance, glyph, popup-data, gui-item, +keymap, charset, color_instance, font_instance, opaque, opaque-list, +process, range-table, specifier, symbol-value-buffer-local, +symbol-value-lisp-magic, symbol-value-varalias, toolbar-button, +tooltalk-message, tooltalk-pattern, window, and window-configuration. We +take care of them in the fist place +in order to be able to handle and to finalize items stored in them more +easily. The function @code{sweep_lcrecords_1} as described below is +doing the whole job for us. +For a description about the internals: @xref{lrecords}. + +Our next candidates are the other objects that behave quite differently +than everything else: the strings. They consists of two parts, a +fixed-size portion (@code{struct Lisp_string}) holding the string's +length, its property list and a pointer to the second part, and the +actual string data, which is stored in string-chars blocks comparable to +frob blocks. In this block, the data is not only freed, but also a +compression of holes is made, i.e. all strings are relocated together. +@xref{String}. This compacting phase is performed by the function +@code{compact_string_chars}, the actual sweeping by the function +@code{sweep_strings} is described below. + +After that, the other types are swept step by step using functions +@code{sweep_conses}, @code{sweep_bit_vectors_1}, +@code{sweep_compiled_functions}, @code{sweep_floats}, +@code{sweep_symbols}, @code{sweep_extents}, @code{sweep_markers} and +@code{sweep_extents}. They are the fixed-size types cons, floats, +compiled-functions, symbol, marker, extent, and event stored in +so-called "frob blocks", and therefore we can basically do the same on +every type objects, using the same macros, especially defined only to +handle everything with respect to fixed-size blocks. The only fixed-size +type that is not handled here are the fixed-size portion of strings, +because we took special care of them earlier. + +The only big exceptions are bit vectors stored differently and +therefore treated differently by the function @code{sweep_bit_vectors_1} +described later. + +At first, we need some brief information about how +these fixed-size types are managed in general, in order to understand +how the sweeping is done. They have all a fixed size, and are therefore +stored in big blocks of memory - allocated at once - that can hold a +certain amount of objects of one type. The macro +@code{DECLARE_FIXED_TYPE_ALLOC} creates the suitable structures for +every type. More precisely, we have the block struct +(holding a pointer to the previous block @code{prev} and the +objects in @code{block[]}), a pointer to current block +(@code{current_..._block)}) and its last index +(@code{current_..._block_index}), and a pointer to the free list that +will be created. Also a macro @code{FIXED_TYPE_FROM_BLOCK} plus some +related macros exists that are used to obtain a new object, either from +the free list @code{ALLOCATE_FIXED_TYPE_1} if there is an unused object +of that type stored or by allocating a completely new block using +@code{ALLOCATE_FIXED_TYPE_FROM_BLOCK}. + +The rest works as follows: all of them define a +macro @code{UNMARK_...} that is used to unmark the object. They define a +macro @code{ADDITIONAL_FREE_...} that defines additional work that has +to be done when converting an object from in use to not in use (so far, +only markers use it in order to unchain them). Then, they all call +the macro @code{SWEEP_FIXED_TYPE_BLOCK} instantiated with their type name +and their struct name. + +This call in particular does the following: we go over all blocks +starting with the current moving towards the oldest. +For each block, we look at every object in it. If the object already +freed (checked with @code{FREE_STRUCT_P} using the first pointer of the +object), or if it is +set to read only (@code{C_READONLY_RECORD_HEADER_P}, nothing must be +done. If it is unmarked (checked with @code{MARKED_RECORD_HEADER_P}), it +is put in the free list and set free (using the macro +@code{FREE_FIXED_TYPE}, otherwise it stays in the block, but is unmarked +(by @code{UNMARK_...}). While going through one block, we note if the +whole block is empty. If so, the whole block is freed (using +@code{xfree}) and the free list state is set to the state it had before +handling this block. + +@node sweep_lcrecords_1 +@subsection @code{sweep_lcrecords_1} +@cindex @code{sweep_lcrecords_1} + +After nullifying the complete lcrecord statistics, we go over all +lcrecords two separate times. They are all chained together in a list with +a head called @code{all_lcrecords}. + +The first loop calls for each object its @code{finalizer} method, but only +in the case that it is not read only +(@code{C_READONLY_RECORD_HEADER_P)}, it is not already marked +(@code{MARKED_RECORD_HEADER_P}), it is not already in a free list (list of +freed objects, field @code{free}) and finally it owns a finalizer +method. + +The second loop actually frees the appropriate objects again by iterating +through the whole list. In case an object is read only or marked, it +has to persist, otherwise it is manually freed by calling +@code{xfree}. During this loop, the lcrecord statistics are kept up to +date by calling @code{tick_lcrecord_stats} with the right arguments, + +@node compact_string_chars +@subsection @code{compact_string_chars} +@cindex @code{compact_string_chars} + +The purpose of this function is to compact all the data parts of the +strings that are held in so-called @code{string_chars_block}, i.e. the +strings that do not exceed a certain maximal length. + +The procedure with which this is done is as follows. We are keeping two +positions in the @code{string_chars_block}s using two pointer/integer +pairs, namely @code{from_sb}/@code{from_pos} and +@code{to_sb}/@code{to_pos}. They stand for the actual positions, from +where to where, to copy the actually handled string. + +While going over all chained @code{string_char_block}s and their held +strings, staring at @code{first_string_chars_block}, both pointers +are advanced and eventually a string is copied from @code{from_sb} to +@code{to_sb}, depending on the status of the pointed at strings. + +More precisely, we can distinguish between the following actions. +@itemize @bullet +@item +The string at @code{from_sb}'s position could be marked as free, which +is indicated by an invalid pointer to the pointer that should point back +to the fixed size string object, and which is checked by +@code{FREE_STRUCT_P}. In this case, the @code{from_sb}/@code{from_pos} +is advanced to the next string, and nothing has to be copied. +@item +Also, if a string object itself is unmarked, nothing has to be +copied. We likewise advance the @code{from_sb}/@code{from_pos} +pair as described above. +@item +In all other cases, we have a marked string at hand. The string data +must be moved from the from-position to the to-position. In case +there is not enough space in the actual @code{to_sb}-block, we advance +this pointer to the beginning of the next block before copying. In case the +from and to positions are different, we perform the +actual copying using the library function @code{memmove}. +@end itemize + +After compacting, the pointer to the current +@code{string_chars_block}, sitting in @code{current_string_chars_block}, +is reset on the last block to which we moved a string, +i.e. @code{to_block}, and all remaining blocks (we know that they just +carry garbage) are explicitly @code{xfree}d. + +@node sweep_strings +@subsection @code{sweep_strings} +@cindex @code{sweep_strings} + +The sweeping for the fixed sized string objects is essentially exactly +the same as it is for all other fixed size types. As before, the freeing +into the suitable free list is done by using the macro +@code{SWEEP_FIXED_SIZE_BLOCK} after defining the right macros +@code{UNMARK_string} and @code{ADDITIONAL_FREE_string}. These two +definitions are a little bit special compared to the ones used +for the other fixed size types. + +@code{UNMARK_string} is defined the same way except some additional code +used for updating the bookkeeping information. + +For strings, @code{ADDITIONAL_FREE_string} has to do something in +addition: in case, the string was not allocated in a +@code{string_chars_block} because it exceeded the maximal length, and +therefore it was @code{malloc}ed separately, we know also @code{xfree} +it explicitly. + +@node sweep_bit_vectors_1 +@subsection @code{sweep_bit_vectors_1} +@cindex @code{sweep_bit_vectors_1} + +Bit vectors are also one of the rare types that are @code{malloc}ed +individually. Consequently, while sweeping, all further needless +bit vectors must be freed by hand. This is done, as one might imagine, +the expected way: since they are all registered in a list called +@code{all_bit_vectors}, all elements of that list are traversed, +all unmarked bit vectors are unlinked by calling @code{xfree} and all of +them become unmarked. +In addition, the bookkeeping information used for garbage +collector's output purposes is updated. + @node Integers and Characters @section Integers and Characters @@ -7402,6 +7904,7 @@ @menu * Critical Redisplay Sections:: * Line Start Cache:: +* Redisplay Piece by Piece:: @end menu @node Critical Redisplay Sections @@ -7497,7 +8000,58 @@ In case you're wondering, the Second Golden Rule of Redisplay is not applicable. -@node Extents, Faces and Glyphs, The Redisplay Mechanism, Top +@node Redisplay Piece by Piece +@section Redisplay Piece by Piece +@cindex Redisplay Piece by Piece + +As you can begin to see redisplay is complex and also not well +documented. Chuck no longer works on XEmacs so this section is my take +on the workings of redisplay. + +Redisplay happens in three phases: + +@enumerate +@item +Determine desired display in area that needs redisplay. +Implemented by @code{redisplay.c} +@item +Compare desired display with current display +Implemented by @code{redisplay-output.c} +@item +Output changes Implemented by @code{redisplay-output.c}, +@code{redisplay-x.c}, @code{redisplay-msw.c} and @code{redisplay-tty.c} +@end enumerate + +Steps 1 and 2 are device-independant and relatively complex. Step 3 is +mostly device-dependent. + +Determining the desired display + +Display attributes are stored in @code{display_line} structures. Each +@code{display_line} consists of a set of @code{display_block}'s and each +@code{display_block} contains a number of @code{rune}'s. Generally +dynarr's of @code{display_line}'s are held by each window representing +the current display and the desired display. + +The @code{display_line} structures are tighly tied to buffers which +presents a problem for redisplay as this connection is bogus for the +modeline. Hence the @code{display_line} generation routines are +duplicated for generating the modeline. This means that the modeline +display code has many bugs that the standard redisplay code does not. + +The guts of @code{display_line} generation are in +@code{create_text_block}, which creates a single display line for the +desired locale. This incrementally parses the characters on the current +line and generates redisplay structures for each. + +Gutter redisplay is different. Because the data to display is stored in +a string we cannot use @code{create_text_block}. Instead we use +@code{create_text_string_block} which performs the same function as +@code{create_text_block} but for strings. Many of the complexities of +@code{create_text_block} to do with cursor handling and selective +display have been removed. + +@node Extents, Faces, The Redisplay Mechanism, Top @chapter Extents @menu @@ -7785,12 +8339,74 @@ stack-of-extents code, which does the heavy-duty algorithmic work of determining which extents overly a particular position. -@node Faces and Glyphs, Specifiers, Extents, Top -@chapter Faces and Glyphs +@node Faces, Glyphs, Extents, Top +@chapter Faces Not yet documented. -@node Specifiers, Menus, Faces and Glyphs, Top +@node Glyphs, Specifiers, Faces, Top +@chapter Glyphs + +Glyphs are graphical elements that can be displayed in XEmacs buffers or +gutters. We use the term graphical element here in the broadest possible +sense since glyphs can be as mundane as text to as arcane as a native +tab widget. + +In XEmacs, glyphs represent the uninstantiated state of graphical +elements, i.e. they hold all the information necessary to produce an +image on-screen but the image does not exist at this stage. + +Glyphs are lazily instantiated by calling one of the glyph +functions. This usually occurs within redisplay when +@code{Fglyph_height} is called. Instantiation causes an image-instance +to be created and cached. This cache is on a device basis for all glyphs +except glyph-widgets, and on a window basis for glyph widgets. The +caching is done by @code{image_instantiate} and is necessary because it +is generally possible to display an image-instance in multiple +domains. For instance if we create a Pixmap, we can actually display +this on multiple windows - even though we only need a single Pixmap +instance to do this. If caching wasn't done then it would be necessary +to create image-instances for every displayable occurrance of a glyph - +and every usage - and this would be extremely memory and cpu intensive. + +Widget-glyphs (a.k.a native widgets) are not cached in this way. This is +because widget-glyph image-instances on screen are toolkit windows, and +thus cannot be reused in multiple XEmacs domains. Thus widget-glyphs are +cached on a window basis. + +Any action on a glyph first consults the cache before actually +instantiating a widget. + +@section Widget-Glyphs in the MS-WIndows Environment + +To Do + +@section Widget-Glyphs in the X Environment + +Widget-glyphs under X make heavy use of lwlib for manipulating the +native toolkit objects. This is primarily so that different toolkits can +be supported for widget-glyphs, just as they are supported for features +such as menubars etc. + +Lwlib is extremely poorly documented and quite hairy so here is my +understanding of what goes on. + +Lwlib maintains a set of widget_instances which mirror the hierarchical +state of Xt widgets. I think this is so that widgets can be updated and +manipulated generically by the lwlib library. For instance +update_one_widget_instance can cope with multiple types of widget and +multiple types of toolkit. Each element in the widget hierarchy is updated +from its corresponding widget_instance by walking the widget_instance +tree recursively. + +This has desirable properties such as lw_modify_all_widgets which is +called from glyphs-x.c and updates all the properties of a widget +without having to know what the widget is or what toolkit it is from. +Unfortunately this also has hairy properrties such as making the lwlib +code quite complex. And of course lwlib has to know at some level what +the widget is and how to set its properties. + +@node Specifiers, Menus, Glyphs, Top @chapter Specifiers Not yet documented. diff -r 28d9c139be4c -r 11054d720c21 man/lispref/hash-tables.texi --- a/man/lispref/hash-tables.texi Mon Aug 13 11:25:03 2007 +0200 +++ b/man/lispref/hash-tables.texi Mon Aug 13 11:26:11 2007 +0200 @@ -72,19 +72,25 @@ (without the @code{:} character), as well as the additional keyword @code{data}, which specifies the initial hash table contents. -@defun make-hash-table &key @code{:size} @code{:test} @code{:type} @code{:rehash-size} @code{:rehash-threshold} +@defun make-hash-table &key @code{test} @code{size} @code{rehash-size} @code{rehash-threshold} @code{weakness} This function returns a new empty hash table object. -Keyword @code{:size} specifies the number of keys likely to be inserted. -This number of entries can be inserted without enlarging the hash table. - Keyword @code{:test} can be @code{eq}, @code{eql} (default) or @code{equal}. Comparison between keys is done using this function. If speed is important, consider using @code{eq}. When storing strings in the hash table, you will likely need to use @code{equal}. -Keyword @code{:type} can be @code{non-weak} (default), @code{weak}, -@code{key-weak} or @code{value-weak}. +Keyword @code{:size} specifies the number of keys likely to be inserted. +This number of entries can be inserted without enlarging the hash table. + +Keyword @code{:rehash-size} must be a float greater than 1.0, and specifies +the factor by which to increase the size of the hash table when enlarging. + +Keyword @code{:rehash-threshold} must be a float between 0.0 and 1.0, +and specifies the load factor of the hash table which triggers enlarging. + +Keyword @code{:weakness} can be @code{nil} (default), @code{t}, +@code{key} or @code{value}. A weak hash table is one whose pointers do not count as GC referents: for any key-value pair in the hash table, if the only remaining pointer @@ -104,12 +110,6 @@ unmarked outside of weak hash tables. The pair will remain in the hash table if the value is pointed to by something other than a weak hash table, even if the key is not. - -Keyword @code{:rehash-size} must be a float greater than 1.0, and specifies -the factor by which to increase the size of the hash table when enlarging. - -Keyword @code{:rehash-threshold} must be a float between 0.0 and 1.0, -and specifies the load factor of the hash table which triggers enlarging. @end defun @defun copy-hash-table hash-table @@ -122,22 +122,16 @@ This function returns the number of entries in @var{hash-table}. @end defun +@defun hash-table-test hash-table +This function returns the test function of @var{hash-table}. +This can be one of @code{eq}, @code{eql} or @code{equal}. +@end defun + @defun hash-table-size hash-table This function returns the current number of slots in @var{hash-table}, whether occupied or not. @end defun -@defun hash-table-type hash-table -This function returns the type of @var{hash-table}. -This can be one of @code{non-weak}, @code{weak}, @code{key-weak} or -@code{value-weak}. -@end defun - -@defun hash-table-test hash-table -This function returns the test function of @var{hash-table}. -This can be one of @code{eq}, @code{eql} or @code{equal}. -@end defun - @defun hash-table-rehash-size hash-table This function returns the current rehash size of @var{hash-table}. This is a float greater than 1.0; the factor by which @var{hash-table} @@ -150,6 +144,11 @@ @var{hash-table}, beyond which the @var{hash-table} is enlarged by rehashing. @end defun +@defun hash-table-weakness hash-table +This function returns the weakness of @var{hash-table}. +This can be one of @code{nil}, @code{t}, @code{key} or @code{value}. +@end defun + @node Working With Hash Tables @section Working With Hash Tables @@ -181,6 +180,7 @@ processed by @var{function}. @end defun + @node Weak Hash Tables @section Weak Hash Tables @cindex hash table, weak @@ -220,5 +220,5 @@ Also see @ref{Weak Lists}. -Weak hash tables are created by specifying the @code{:type} keyword to +Weak hash tables are created by specifying the @code{:weakness} keyword to @code{make-hash-table}. diff -r 28d9c139be4c -r 11054d720c21 man/xemacs-faq.texi --- a/man/xemacs-faq.texi Mon Aug 13 11:25:03 2007 +0200 +++ b/man/xemacs-faq.texi Mon Aug 13 11:26:11 2007 +0200 @@ -7,7 +7,7 @@ @finalout @titlepage @title XEmacs FAQ -@subtitle Frequently asked questions about XEmacs @* Last Modified: $Date: 1999/05/13 12:26:40 $ +@subtitle Frequently asked questions about XEmacs @* Last Modified: $Date: 1999/10/24 09:05:29 $ @sp 1 @author Tony Rossini @author Ben Wing @@ -580,7 +580,7 @@ @unnumberedsubsec Q1.0.6: Where can I get help? Probably the easiest way, if everything is installed, is to use info, by -pressing @kbd{C-h i}, or selecting @code{Emacs Info} from the Help Menu. +pressing @kbd{C-h i}, or selecting @code{Manuals->Info} from the Help Menu. Also, @kbd{M-x apropos} will look for commands for you. @@ -1148,9 +1148,9 @@ home directory and rename it @file{.emacs}. Then edit it to suit. Starting with 19.14, you may bring the @file{sample.emacs} into an -XEmacs buffer by selecting @samp{Help->Sample .emacs} from the menubar. -To determine the location of the @file{etc} directory type the command -@kbd{C-h v data-directory @key{RET}}. +XEmacs buffer by selecting @samp{Help->Samples->Sample .emacs} from the +menubar. To determine the location of the @file{etc} directory type the +command @kbd{C-h v data-directory @key{RET}}. @node Q1.4.2, Q1.4.3, Q1.4.1, Introduction @unnumberedsubsec Q1.4.2: Can I use the same @file{.emacs} with the other Emacs? @@ -1161,10 +1161,10 @@ @node Q1.4.3, Q1.4.4, Q1.4.2, Introduction @unnumberedsubsec Q1.4.3: Any good tutorials around? -There's the XEmacs tutorial available from the Help Menu, or by typing -@kbd{C-h t}. To check whether it's available in a non-english language, -type @kbd{C-u C-h t TAB}, type the first letters of your preferred -language, then type @key{RET}. +There's the XEmacs tutorial available from the Help Menu under +@samp{Basics->Tutorials}, or by typing @kbd{C-h t}. To check whether +it's available in a non-english language, type @kbd{C-u C-h t TAB}, type +the first letters of your preferred language, then type @key{RET}. There's an Emacs Lisp tutorial at @@ -1580,7 +1580,7 @@ No. The name @dfn{XEmacs} is unfortunate in the sense that it is @strong{not} an X Window System-only version of Emacs. Starting with -19.14 XEmacs has full color support on a color capable character +19.14 XEmacs has full color support on a color-capable character terminal. @node Q2.0.6, Q2.0.7, Q2.0.5, Installation @@ -5112,6 +5112,10 @@ rename-uniquely} to rename the @code{*shell*} buffer instead of @kbd{M-x rename-buffer}. +Alternately, you can set the variable @code{shell-multiple-shells}. +If the value of this variable is non-nil, each time shell mode is invoked, +a new shell is made + @node Q5.0.7, Q5.0.8, Q5.0.6, Miscellaneous @unnumberedsubsec Q5.0.7: Telnet from shell filters too much diff -r 28d9c139be4c -r 11054d720c21 man/xemacs/cmdargs.texi --- a/man/xemacs/cmdargs.texi Mon Aug 13 11:25:03 2007 +0200 +++ b/man/xemacs/cmdargs.texi Mon Aug 13 11:26:11 2007 +0200 @@ -155,10 +155,17 @@ @item -vanilla This is equivalent to @samp{-q -no-site-file -no-early-packages}. +@item -user-init-file @var{file} +Load @var{file} as your Emacs init file instead of @file{~/.emacs}. + +@item -user-init-directory @var{directory} +Use @var{directory} as the location of your early package hierarchies +and the various user-specific initialization files. + @item -user @var{user} @itemx -u @var{user} -Load @var{user}'s Emacs init file @file{~@var{user}/.emacs} instead of -your own. +Equivalent to +@samp{-user-init-file ~@var{user}/.emacs -user-init-directory ~@var{user}/.xemacs}. @end table diff -r 28d9c139be4c -r 11054d720c21 man/xemacs/custom.texi --- a/man/xemacs/custom.texi Mon Aug 13 11:25:03 2007 +0200 +++ b/man/xemacs/custom.texi Mon Aug 13 11:26:11 2007 +0200 @@ -1539,18 +1539,13 @@ When you start Emacs, it normally loads the file @file{.emacs} in your home directory. This file, if it exists, should contain Lisp code. It is called your initialization file or @dfn{init file}. Use the command -line switches @samp{-q} and @samp{-u} to tell Emacs whether to load an -init file (@pxref{Entering Emacs}). - -@vindex init-file-user -When the @file{.emacs} file is read, the variable @code{init-file-user} -says which user's init file it is. The value may be the null string or a -string containing a user's name. If the value is a null string, it means -that the init file was taken from the user that originally logged in. - -In all cases, @code{(concat "~" init-file-user "/")} evaluates to the -directory name of the directory where the @file{.emacs} file was looked -for. +line switch @samp{-q} to tell Emacs whether to load an +init file (@pxref{Entering Emacs}). Use the command line switch +@samp{-user-init-file} (@pxref{Command Switches}) to tell Emacs to load +a different file instead of @file{~/.emacs}. + +When the @file{.emacs} file is read, the variable @code{user-init-file} +says which init file was loaded. At some sites there is a @dfn{default init file}, which is the library named @file{default.el}, found via the standard search path for diff -r 28d9c139be4c -r 11054d720c21 man/xemacs/packages.texi --- a/man/xemacs/packages.texi Mon Aug 13 11:25:03 2007 +0200 +++ b/man/xemacs/packages.texi Mon Aug 13 11:26:11 2007 +0200 @@ -116,6 +116,17 @@ idea to install all packages and not interfere with the wishes of your users. +If you can't find which package provides the feature you require, try +using the @code{package-get-package-provider} function. Eg., if you know +that you need @code{thingatpt}, type: + +@example +M-x package-get-package-provider RET thingatpt +@end example + +which will return something like (fsf-compat "1.06"). You can the use +one of the methods above for installing the package you want. + @subsection XEmacs and Installing Packages Normally, packages are installed over the network, using EFS diff -r 28d9c139be4c -r 11054d720c21 man/xemacs/programs.texi --- a/man/xemacs/programs.texi Mon Aug 13 11:25:03 2007 +0200 +++ b/man/xemacs/programs.texi Mon Aug 13 11:26:11 2007 +0200 @@ -884,7 +884,7 @@ @findex insert-parentheses @findex move-over-close-and-reindent The commands @kbd{M-(} (@code{insert-parentheses}) and @kbd{M-)} -(@code{move-over-close-@*and-reindent}) are designed to facilitate a style of +(@code{move-over-close-and-reindent}) are designed to facilitate a style of editing which keeps parentheses balanced at all times. @kbd{M-(} inserts a pair of parentheses, either together as in @samp{()}, or, if given an argument, around the next several sexps, and leaves point after the open diff -r 28d9c139be4c -r 11054d720c21 modules/base64/.cvsignore --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/modules/base64/.cvsignore Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,2 @@ +*.ell +*_i.c diff -r 28d9c139be4c -r 11054d720c21 modules/base64/Makefile --- a/modules/base64/Makefile Mon Aug 13 11:25:03 2007 +0200 +++ b/modules/base64/Makefile Mon Aug 13 11:26:11 2007 +0200 @@ -25,6 +25,8 @@ all: $(MODNAME).ell +distclean: clean + clean: rm -f $(MODNAME).ell $(OBJS) base64_i.o base64_i.c diff -r 28d9c139be4c -r 11054d720c21 modules/ldap/.cvsignore --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/modules/ldap/.cvsignore Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,2 @@ +*.ell +*_i.c diff -r 28d9c139be4c -r 11054d720c21 modules/ldap/Makefile --- a/modules/ldap/Makefile Mon Aug 13 11:25:03 2007 +0200 +++ b/modules/ldap/Makefile Mon Aug 13 11:26:11 2007 +0200 @@ -25,6 +25,8 @@ all: $(MODNAME).ell +distclean: clean + clean: rm -f $(MODNAME).ell $(OBJS) eldap_i.o eldap_i.c diff -r 28d9c139be4c -r 11054d720c21 modules/sample/.cvsignore --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/modules/sample/.cvsignore Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,2 @@ +*.ell +*_i.c diff -r 28d9c139be4c -r 11054d720c21 modules/sample/Makefile --- a/modules/sample/Makefile Mon Aug 13 11:25:03 2007 +0200 +++ b/modules/sample/Makefile Mon Aug 13 11:26:11 2007 +0200 @@ -25,6 +25,8 @@ all: $(MODNAME).ell +distclean: clean + clean: rm -f $(MODNAME).ell $(OBJS) sample_i.o sample_i.c diff -r 28d9c139be4c -r 11054d720c21 modules/zlib/.cvsignore --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/modules/zlib/.cvsignore Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,2 @@ +*.ell +*_i.c \ No newline at end of file diff -r 28d9c139be4c -r 11054d720c21 modules/zlib/Makefile --- a/modules/zlib/Makefile Mon Aug 13 11:25:03 2007 +0200 +++ b/modules/zlib/Makefile Mon Aug 13 11:26:11 2007 +0200 @@ -25,6 +25,8 @@ all: $(MODNAME).ell +distclean: clean + clean: rm -f $(MODNAME).ell $(OBJS) zlib_i.o zlib_i.c diff -r 28d9c139be4c -r 11054d720c21 nt/ChangeLog --- a/nt/ChangeLog Mon Aug 13 11:25:03 2007 +0200 +++ b/nt/ChangeLog Mon Aug 13 11:26:11 2007 +0200 @@ -1,3 +1,29 @@ +1999-11-10 XEmacs Build Bot + + * XEmacs 21.2.20 is released + +1999-10-07 Norbert Koch + + * xemacs.mak: Ignore return code of 'del' calls. Use a make + variable for 'del'. + +1999-09-26 Adrian Aichner + + * xemacs.mak (all): Update $(LISP)/auto-autoloads.elc? and + $(LISP)/custom-load.el using XEmacs itself, like xemacs-packages + do. + ($(LISP)\auto-autoloads.el): Add new rule. + ($(LISP)\custom-load.el): Ditto. + +1999-08-04 Andy Piper + + * xemacs.mak (HAVE_WIDGETS): add define to appropriate places. + +1999-07-26 Adrian Aichner + + * xemacs.mak ($(MANDIR)\lispref\lispref.texi): Replace bad + dependency. + 1999-07-30 XEmacs Build Bot * XEmacs 21.2.19 is released diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/README --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/README Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,31 @@ +To use: + +You need to build and install the XEmacs distribution. Also you need +the xemacs packages in both source and installed versions. + +Edit "dirs.py" to reflect the locations of the above components. + +Edit "version.py" to reflect the current version, as well as the +welcome message. + +Run + python pre_wise.py > xemacs-XXX.wse + + (for XXX use a version or date code of your choosing) + +Run + cmd /c xemacs-XXX.wse + +to produce xemacs-XXX.exe + + +"pre_wise.py" is a preprocessor for the Wise installer maker. It +reads "xemacs.tmpl" which is a Wise input file, except that certain +portions are enclosed in triple angle brackets <<>> + +These portions are evaluated as Python expressions and replaced by the +string representations of the resulting value. This allows for +things to change from release to release without having to re-do the +Wise installation each time. Also it keeps you from having to +manually drag-n-drop all the package files, which is rather tedious! + diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/dirs.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/dirs.py Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,21 @@ +#Configuration variables + +#where the source is: + +source = r"X:\XEmacs-21" +#where the installed distribution is: +installed = r"C:\Program Files\XEmacs\xemacs-21.0-b62" + +#where the (built and installed) packages are +packages = r"C:\Program Files\XEmacs\xemacs-packages" + +#where the package source is +pkg_src = r"X:\xemacs-packages" + +#Subdirs relative to the base installation directory +#Everything except packages goes here: +dst = "XEmacs-21.0-b62" +#packages go here: +pkg_dst = "xemacs-packages" + + diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/display readme.dlg --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/display readme.dlg Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,63 @@ +Document Type: DLG +item: Custom Dialog + Name=Display ReadMe + Display Variable=DISPLAY + item: Dialog + Title=Read Me File + Title French=Fichier Lisez-moi + Title German=Liesmich-Datei + Title Portuguese=Ficheiro Leia-me + Title Spanish=Archivo Léeme + Title Italian=File Leggimi + Title Danish=Vigtigt fil + Title Dutch=Leesmij-bestand + Title Norwegian=Informasjonsfil + Title Swedish=Läs mig-fil + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=172 185 214 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=I &Agree > + Text French=&Suivant> + Text German=&Weiter> + Text Portuguese=&Próximo> + Text Spanish=&Siguiente > + Text Italian=&Avanti > + Text Danish=&Næste> + Text Dutch=&Volgende> + Text Norwegian=&Neste> + Text Swedish=&Nästa > + end + item: Push Button + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Slet + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Editbox + Rectangle=85 11 254 170 + Value=%TEMP%\%READMEFILE% + Help Context=16711681 + Create Flags=01010000101000000000100000000100 + end + end +end diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/el.reg --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/el.reg Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,36 @@ + +REGEDIT4 + +[HKEY_CLASSES_ROOT\.el] +@="elfile" +"Content Type"="text/plain" + +[HKEY_CLASSES_ROOT\elfile] +@="Emacs lisp" +"EditFlags"=hex:00,00,01,00 + +[HKEY_CLASSES_ROOT\elfile\Shell] +@="" + +[HKEY_CLASSES_ROOT\elfile\Shell\open] + +[HKEY_CLASSES_ROOT\elfile\Shell\open\command] +@="\"C:\\Program Files\\XEmacs\\XEmacs-21.0\\i386-pc-win32\\runemacs.exe\" \"%1\"" + +[HKEY_CLASSES_ROOT\elfile\Shell\open\ddeexec] +@="open(\"%1\")" + +[HKEY_CLASSES_ROOT\elfile\Shell\open\ddeexec\Application] +@="XEmacs" + +[HKEY_CLASSES_ROOT\elfile\Shell\open\ddeexec\topic] +@="System" + +[HKEY_CLASSES_ROOT\elfile\DefaultIcon] +@="C:\\Program Files\\XEmacs\\XEmacs-21.0\\i386-pc-win32\\runemacs.exe,2" + +[HKEY_CLASSES_ROOT\elfile\QuickView] +@="*" + + + diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/filelist.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/filelist.py Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,23 @@ +import os +import dirs +import string + +def listdir_recursive(basedir): + ret = [] + for f in os.listdir(basedir): + if os.path.isfile(basedir+"\\"+f): + ret.append(f) + elif os.path.isdir(basedir+"\\"+f): + for f1 in listdir_recursive(basedir+"\\"+f): + ret.append(f+"\\"+f1) + return ret + +all = [] + + + +for f in listdir_recursive(dirs.installed): + if string.find(f,'CVS')>=0: + continue + all.append((f, dirs.installed, dirs.dst)) + diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/files.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/files.py Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,36 @@ +import os +import dirs + +def listdir_recursive(basedir): + ret = [] + for f in os.listdir(basedir): + if os.path.isfile(basedir+"\\"+f): + ret.append(f) + elif os.path.isdir(basedir+"\\"+f): + for f1 in listdir_recursive(basedir+"\\"+f): + ret.append(f+"\\"+f1) + return ret + +install = [] + +for f in os.listdir(dirs.source+"\\lib-src"): + if f == "DOC" or f[-4:]==".exe": + install.append((f,dirs.source+"\\lib-src",dirs.bin_dst)) + + +for f in ['runemacs.exe', 'xemacs.exe']: + install.append((f,dirs.source+"\\src",dirs.bin_dst)) + +for f in listdir_recursive(dirs.source+"\\lisp"): + install.append((f,dirs.source+"\\lisp",dirs.lisp_dst)) + +for f in listdir_recursive(dirs.source+"\\etc"): + install.append((f,dirs.source+"\\etc",dirs.etc_dst)) + + +for f in os.listdir(dirs.source+"\\info"): + install.append((f,dirs.source+"\\info",dirs.info_dst)) + + + + diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/gnu.bmp Binary file nt/installer/Wise/gnu.bmp has changed diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/libs.dlg --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/libs.dlg Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,170 @@ +Document Type: DLG +item: Custom Dialog + Name=Select Components + Display Variable=DISPLAY + Flags=00000001 + item: Dialog + Title=Select Components + Title French=Sélectionner les éléments + Title German=Komponenten auswählen + Title Portuguese=Seleccionar Componentes + Title Spanish=Seleccione los Componentes + Title Italian=Seleziona Componenti + Title Danish=Vælg komponenter + Title Dutch=Selecteer onderdelen + Title Norwegian=Velg komponenter + Title Swedish=Välj komponenter + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=172 185 214 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=&Next > + Text French=&Suivant> + Text German=&Weiter> + Text Portuguese=&Próximo> + Text Spanish=&Siguiente > + Text Italian=&Avanti > + Text Danish=&Næste> + Text Dutch=&Volgende> + Text Norwegian=&Neste> + Text Swedish=&Nästa > + end + item: Push Button + Rectangle=130 185 172 199 + Variable=DIRECTION + Value=B + Create Flags=01010000000000010000000000000000 + Text=< &Back + Text French=<&Retour + Text German=<&Zurück + Text Portuguese=<&Retornar + Text Spanish=<&Retroceder + Text Italian=< &Indietro + Text Danish=<&Tilbage + Text Dutch=<&Terug + Text Norwegian=<&Tilbake + Text Swedish=< &Tillbaka + end + item: Push Button + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Annuller + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=205 156 253 166 + Variable=COMPONENTS + Value=MAINDIR + Create Flags=01010000000000000000000000000010 + end + item: Static + Rectangle=205 148 253 157 + Variable=COMPONENTS + Create Flags=01010000000000000000000000000010 + end + item: Static + Rectangle=95 147 184 158 + Create Flags=01010000000000000000000000000000 + Text=Disk Space Required: + Text French=Espace disque requis + Text German=Benötigter Festplattenspeicher: + Text Portuguese=Espaço de disco necessário: + Text Spanish=Espacio de Disco Requerido: + Text Italian=Spazio su disco richiesto: + Text Danish=Nødvendig diskplads: + Text Dutch=Vereiste hoeveelheid schijfruimte + Text Norwegian=Diskplass nødvendig: + Text Swedish=Erforderligt diskutrymme + end + item: Static + Rectangle=95 157 190 167 + Create Flags=01010000000000000000000000000000 + Text=Disk Space Remaining: + Text French=Espace disque disponible + Text German=Verbleibender Festplattenspeicher: + Text Portuguese=Espaço de disco restante: + Text Spanish=Espacio de Disco Remanente: + Text Italian=Spazio su disco rimanente: + Text Danish=Ledig diskplads: + Text Dutch=Resterende schijfruimte + Text Norwegian=Ledig diskplass: + Text Swedish=Återstående diskutrymme + end + item: Static + Rectangle=90 138 264 168 + Action=1 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=90 8 260 41 + Create Flags=01010000000000000000000000000000 + Text=In the options list below, select the checkboxes for the options that you would like to have installed. The disk space fields reflect the requirements of the options you have selected. + Text French=Dans la liste d'options suivante, veuillez sélectionner les cases des options que vous désirez installer. Le champ d'espace disque indique les conditions requises pour les options choisies + Text German=Wählen Sie in der Optionenliste unten die Kontrollkästchen für diejenigen Optionen, die Sie installieren möchten. Die Speicherfelder zeigen die benötigte Speicherkapazität für die gewählten Optionen an. + Text Portuguese=Na lista de opções abaixo, seleccione as caixas de verificação para as opções que gostaria de ter instalado. Os campos de espaço de disco reflectem os requerimentos das opções que seleccionou. + Text Spanish=En la lista de opciones que se ofrece a continuación, seleccione las casillas de comprobación para las opciones que desea instalar. Los campos del espacio en el disco reflejan los requerimientos de las opciones que ha seleccionado. + Text Italian=Nell’elenco delle opzioni sotto, marca le caselle di controllo delle opzioni che vuoi installare. I campi dello spazio sul disco riflettono i requisiti delle opzioni selezionate. + Text Danish=Marker afkrydsningsfelterne for de komponenter, der skal installeres, på listen herunder. Diskpladsfelterne angiver pladskravene for de valgte komponenter. + Text Dutch=Kruis in de onderstaande lijst het vakje aan naast de opties die u wilt installeren. Achter elke optie staat de benodigde schijfruimte vermeld. + Text Norwegian=I listen over alternativer nedenfor, klikk i kontrollrutene for de alternativene du ønsker å installere. Diskplassfeltene gjenspeiler kravene for de alternativene du har valgt. + Text Swedish=Kryssa för i rutorna nedan vilka alternativ du vill få installerade. I diskutrymmesfälten anges utrymmesbehoven för de alternativ du väljer. + end + item: Checkbox + Rectangle=91 41 126 56 + Variable=COMPONENTS LIBS + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000010000000000000011 + Flags=0000000000000010 + Text=Libraries + Text= + end + item: Checkbox + Rectangle=90 56 148 71 + Variable=COMPONENTS COMM + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000010000000000000011 + Flags=0000000000000010 + Text=Communications + Text= + end + end + item: Dialog + Title=Library Packages + Width=268 + Height=204 + Font Name=Helv + Font Size=8 + end + item: Dialog + Title=Library Packages + Width=268 + Height=204 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=219 170 254 185 + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000010000000000000000 + Text=OK + end + end +end diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/packages.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/packages.py Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,140 @@ +#configuration variables + +#package categories +category_names = ["libs", "comm", "oa", "os", "prog", "wp", "games"] + +category_descriptions = {"libs":"Libraries", + "comm":"Communication", + "oa": "Productivity", #??? + "os": "Operating System", + "prog": "Programming", + "wp": "Word Processing", + "games": "Games and Amusements"} + + +#packages to install by default +default=["xemacs-base","edit-utils","efs", + "text-modes","prog-modes", + "dired","apel", + "c-support","cc-mode", + "mail-lib","pc","sounds-wav"] + +def category_of_letter(x): + return category_names[ord(x)-ord('A')] + +def letter_of_category(cat): + return chr(ord('A')+category_names.index(cat)) + +def letter_of_package(x): + return chr(ord('A')+packages_of_category(category_of_package(x)).index(x)) + +import dirs, os +catpkg = {} +pkgcat = {} + +for cat in category_names: + pkgcat[cat]=[] + dd = os.path.join(dirs.pkg_src,cat) + for d in os.listdir(dd): + if d == "CVS": + continue + manifest = dirs.packages + "\\pkginfo\\MANIFEST." + d + if not os.path.exists(manifest): #it's not installed, skip it + continue + if os.path.isdir(os.path.join(dd,d)): + catpkg[d] = cat + pkgcat[cat].append(d) + +def category_of_package(p): + return catpkg[p] + +def packages_of_category(c): + return pkgcat[c] + +#Brief descriptions of the packages. +#This data is up-to-date as of 13 January 1998. +package_descriptions={ + "Sun":"Support for Sparcworks.", + "apel":"A Portable Emacs Library", + "edebug":"A Lisp debugger", + "dired":"The DIRectory EDitor", + "efs":"Access remote filesystems", + "mail-lib":"Fundamental email support", + "tooltalk":"Tooltalk", + "xemacs-base":"Fundamental XEmacs support", + "xemacs-devel":"Lisp developer support.", + "footnote":"Footnoting in mail messages", + "gnats":"XEmacs bug reports", + "gnus":"Newsreader and Mailreader", + "mailcrypt":"Message encryption with PGP.", + "mh-e":"Support for MH mailreader", + "net-utils":"Networking Utilities", + "ph":"CCSO/qi directory client", + "rmail":"An obsolete Emacs mailer", + "supercite":"Mail/News Citation tool", + "tm":"Emacs MIME support", + "vm":"An Emacs mailer", + "w3":"A Web browser", + "cookie":"Spook and Yow (Zippy quotes)", + "games":"Tetris, Sokoban, and Snake", + "mine":"Minehunt", + "misc-games":"Other amusements and diversions", + "egg-its":"Wnn(4.2 and 6)/SJ3 support", + "leim":"Quail", + "locale":"Localized menubars", + "mule-base":"Basic Mule support", + "skk":"Another Japanese Language Input Method", + "calendar":"Calendar and diary", + "edit-utils":"Various XEmacs goodies", + "forms":"Obsolete forms editing support", + "frame-icon":"Change icon based on mode", + "hm--html-menus":"HTML editing", + "ispell":"Spell-checking with ispell", + "pc":"PC style interface emulation", + "psgml":"Validated HTML/SGML editing", + "sgml":"SGML/Linuxdoc-SGML editing", + "slider":"User interface tool", + "speedbar":"??? Document me.", + "strokes":"Mouse enhancement utility", + "text-modes":"Packages for editing text files", + "time":"Display time and date", + "eterm":"Terminal emulator", + "igrep":"Enhanced Grep", + "ilisp":"Front-end for Inferior Lisp", + "os-utils":"Misc. OS utilities", + "view-process":"Unix process viewer", + "ada":"Ada language support", + "c-support":"Add-ons for editing C code", + "cc-mode":"C, C++ and Java language editing", + "debug": "GUD, gdb, dbx debugging support", + "ediff": "Compare files", + "emerge": "Merge files", + "pcl-cvs":"CVS frontend.", + "prog-modes":"Various programming languages", + "scheme":"Front-end for Inferior Scheme", + "sh-script":"Support for editing shell scripts", + "vc":"Version Control", + "vc-cc":"Broken", + "vhdl":"Support for VHDL", + "auctex":"Basic TeX/LaTeX support", + "crisp":"Crisp/Brief emulation", + "edt":"DEC EDIT/EDT emulation", + "texinfo":"XEmacs TeXinfo support.", + "textools":"TeX support", + "tpu":"DEC EDIT/TPU support", + "viper":"VI emulation", + "elib":"Portable elisp utility library", + "fsf-compat": "FSF Emacs compatibility files", + "sounds-wav": "XEmacs Microsoft sound files", + "bbdb": "The Big Brother Data Base", + "eudc": "Emacs Unified Directory Client", + "mew": "Messaging in an Emacs World", + "zenirc": "IRC client", + "calc": "Emacs calculator", + "jde": "Java development environment", + "reftex": "LaTeX cross-referencing and citations" +} + + + + diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/pre_wise.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/pre_wise.py Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,133 @@ +import string +import re +import os +import types + +infile=open("xemacs.tmpl","r") + +import version +import dirs +import filelist +import packages + +def letter(package): + index = packages.all.index(package) + if index>29: + raise "WISE error: too many components" + return chr(ord("A")+index) + +def letters(package_list): + ret = "" + for p in package_list: + ret = ret+letter(p) + return ret + +def describe(package): + if package in packages.descriptions.keys(): + return ": "+packages.descriptions[package] + else: return "" + +def ifblock(var,val): + return("item: If/While Statement\n Variable=%s\n Value=%s\n Flags=00001010\nend\n" % (var,val)) + +def endblock(): + return("item: End Block\nend\n") + +def setvar(var,val): + return("item: Set Variable\n Variable=%s\n Value=%s\n Flags=10000000\nend\n" % (string.upper(var), val)) + +def default_letters_of_category(cat): + val = "" + for p in packages.default: + if packages.category_of_package(p) == cat: + val = val + packages.letter_of_package(p) + return val + +def set_category_defaults(): + ret = "" + for c in packages.category_names: + ret = ret + setvar(c, default_letters_of_category(c)) + return ret + +def do_category(cat): + ret = ifblock("COMPONENTS", packages.letter_of_category(cat)) + for pkg in packages.packages_of_category(cat): + ret = ret + ifblock(string.upper(cat),packages.letter_of_package(pkg)) + for f in files_of_package(pkg): + ret = ret+install_pkg_file(f) + ret = ret + endblock() + ret = ret + endblock() + return ret + +def files_of_package(package): + manifest_file = dirs.packages + "\\pkginfo\\MANIFEST." + package + manifest = open(manifest_file,"r") + lines = manifest.readlines() + lines = map(lambda s:s[:-1], lines) + lines = map(lambda s:string.replace(s,'/','\\'), lines) + return lines + +def category_dialog(cat): + npkg = len(packages.packages_of_category(cat)) + ret="" + ret=ret+" item: Dialog\n Title="+packages.category_descriptions[cat]+" Packages\n" + ret=ret+" Width=210\n" + ret=ret+" Height=%d\n" % (45+npkg*10) + ret=ret+" Font Name=Helv\n" + ret=ret+" Font Size=8\n" + ret=ret+" item: Push Button\n" + ret=ret+" Rectangle=107 %d 147 %d\n" % (5+npkg*10+2, 5+npkg*10+17) + ret=ret+" Create Flags=01010000000000010000000000000001\n" + ret=ret+" Text=OK\n" + ret=ret+" end\n" + ret=ret+" item: Push Button\n" + ret=ret+" Rectangle=153 %d 193 %d\n" % (5+npkg*10+2, 5+npkg*10+17) + ret=ret+" Variable=%s\n" % string.upper(cat) + ret=ret+" Value=%%%s_SAVE%%\n" % string.upper(cat) + ret=ret+" Create Flags=01010000000000010000000000000000\n" + ret=ret+" Flags=0000000000000001\n" + ret=ret+" Text=Cancel\n" + ret=ret+" end\n" + ret=ret+" item: Checkbox\n" + ret=ret+" Rectangle=0 5 191 %d\n" % (10*npkg) + ret=ret+" Variable=%s\n"%string.upper(cat) + ret=ret+" Create Flags=01010000000000010000000000000011\n" + ret=ret+" Flags=0000000000000010\n" + for pkg in packages.packages_of_category(cat): + ret = ret+" Text=%s: %s\n"%( pkg, packages.package_descriptions[pkg]) + ret=ret+" Text=\n" + ret=ret+" end\n" + ret=ret+" end\n" + return ret + +def src_path(src,name): + return src + "\\" + name + +def dst_path(dst,name): + return "%MAINDIR%"+"\\"+dst+"\\" + name + +def install_file(name,src,dst): + return("item: Install File\n Source=%s\n Destination=%s\n Flags=0000000010000010\nend\n" % (src_path(src,name),dst_path(dst,name))) + +def install_pkg_file(name): + return install_file(name,dirs.packages,dirs.pkg_dst) + +def do_package(package): + return ifblock("COMPONENTS",letter(package)) + \ + string.join(map(install_pkg_file,files(package)),"")+ \ + endblock() + +for line in infile.readlines(): + left=string.find(line,"<<<") + if left>=0: + right=string.find(line,">>>") + expr=line[left+3:right] + val=eval(expr) + if type(val)==types.StringType: + print line[:left] + val + line[right+3:], + elif type(val)==types.ListType: + for v in val: + print line[:left] + v + line[right+3:], + else: print line, + + diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/type.dlg --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/type.dlg Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,32 @@ +Document Type: DLG +item: Custom Dialog + Name=type + item: Dialog + Title=type + Width=238 + Height=208 + Font Name=Helv + Font Size=8 + item: Radio Button + Rectangle=5 5 40 20 + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000010000000000001001 + Text=minimal + Text= + end + item: Radio Button + Rectangle=5 25 40 40 + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000010000000000001001 + Text=custom + Text= + end + item: Radio Button + Rectangle=5 45 40 60 + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000010000000000001001 + Text=full + Text= + end + end +end diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/version.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/version.py Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,3 @@ +title="XEmacs 21.0b62 EXPERIMENTAL" +welcome="Welcome to the %APPTITLE% setup program. Please note that this is an experimental release and some features may not work correctly, especially on machines running Windows 95. Please read the file PROBLEMS in the xemacs installation directory. Send comments or bug reports to xemacs-nt@xemacs.org. For more info see http://www.xemacs.org" + diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/welcome.dlg --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/welcome.dlg Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,63 @@ +Document Type: DLG +item: Custom Dialog + Name=Welcome + Display Variable=DISPLAY + item: Dialog + Title=Welcome + Title French=Bienvenue + Title German=Willkommen + Title Portuguese=Bem-vindo + Title Spanish=Bienvenido + Title Italian=Benvenuto + Title Danish=Velkommen + Title Dutch=Welkom + Title Norwegian=Velkommen + Title Swedish=Välkommen + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=172 185 214 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=&Next > + Text French=&Suivant> + Text German=&Weiter> + Text Portuguese=&Próximo> + Text Spanish=&Siguiente > + Text Italian=&Avanti > + Text Danish=&Næste> + Text Dutch=&Volgende> + Text Norwegian=&Neste> + Text Swedish=&Nästa > + end + item: Push Button + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Annuller + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=91 22 245 118 + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000000000000000000000 + Text=Welcome to the %APPTITLE% setup program. Please note that this is an experimental release and some features may not work correctly. Send comments or bug reports to xemacs-nt@xemacs.org rather than one of the other XEmacs mailing lists. For more info see http://www.xemacs.org + end + end +end diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/xemacs-beta.bmp Binary file nt/installer/Wise/xemacs-beta.bmp has changed diff -r 28d9c139be4c -r 11054d720c21 nt/installer/Wise/xemacs.tmpl --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/nt/installer/Wise/xemacs.tmpl Mon Aug 13 11:26:11 2007 +0200 @@ -0,0 +1,1310 @@ +Document Type: WSE +item: Global + Version=7.0 + Title=<<>> + Flags=00000100 + Languages=65 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 + Japanese Font Name=MS Gothic + Japanese Font Size=10 + Progress Bar DLL=%_WISE_%\Progress\WIZ%_EXE_OS_TYPE_%.DLL + Start Gradient=0 0 255 + End Gradient=0 0 0 + Windows Flags=00000100000000010010110000001000 + Log Pathname=%MAINDIR%\INSTALL.LOG + Message Font=MS Sans Serif + Font Size=8 + Disk Filename=SETUP + Patch Flags=0000000000000001 + Patch Threshold=85 + Patch Memory=4000 + FTP Cluster Size=20 + Dialogs Version=6 + Variable Name1=_SYS_ + Variable Default1=C:\WINDOWS\SYSTEM + Variable Flags1=00001000 + Variable Name2=_WISE_ + Variable Default2=C:\PROGRAM FILES\WISE INSTALLBUILDER + Variable Flags2=00001000 +end +item: Get Temporary Filename + Variable=READMEFILE +end +item: Install File + Source=<<>>\nt\Wise\Copying.txt + Destination=%TEMP%\%READMEFILE% + Flags=0000000000100010 +end +item: Open/Close INSTALL.LOG + Flags=00000001 +end +item: Check if File/Dir Exists + Pathname=%SYS% + Flags=10000100 +end +item: Set Variable + Variable=SYS + Value=%WIN% +end +item: End Block +end +item: Set Variable + Variable=APPTITLE + Value=<<>> + Flags=10000000 +end +item: Set Variable + Variable=GROUP + Value=XEmacs + Flags=10000000 +end +item: Set Variable + Variable=DISABLED + Value=! +end +item: Set Variable + Variable=MAINDIR + Value=XEmacs + Flags=10000000 +end +item: Check Configuration + Flags=10111011 +end +item: Get Registry Key Value + Variable=COMMON + Key=SOFTWARE\Microsoft\Windows\CurrentVersion + Default=C:\Program Files\Common Files + Value Name=CommonFilesDir + Flags=00000100 +end +item: Get Registry Key Value + Variable=PROGRAM_FILES + Key=SOFTWARE\Microsoft\Windows\CurrentVersion + Default=C:\Program Files + Value Name=ProgramFilesDir + Flags=00000100 +end +item: Set Variable + Variable=MAINDIR + Value=%PROGRAM_FILES%\%MAINDIR% + Flags=00001100 +end +item: Set Variable + Variable=EXPLORER + Value=1 +end +item: Else Statement +end +item: Set Variable + Variable=MAINDIR + Value=C:\%MAINDIR% + Flags=00001100 +end +item: End Block +end +item: Set Variable + Variable=BACKUP + Value=%MAINDIR%\BACKUP + Flags=10000000 +end +item: Set Variable + Variable=DOBACKUP + Value=B + Flags=10000000 +end +item: Set Variable + Variable=COMPONENTS + Value=ACE + Flags=10000000 +end +<<>> +item: Wizard Block + Direction Variable=DIRECTION + Display Variable=DISPLAY + Bitmap Pathname=<<>>\nt\Wise\gnu.bmp + X Position=9 + Y Position=10 + Filler Color=8421440 + Dialog=Select Program Manager Group + Dialog=Select Backup Directory + Dialog=Display Registration Information + Dialog=Get Registration Information + Variable=EXPLORER + Variable=DOBACKUP + Variable=DOBRAND + Variable=DOBRAND + Value=1 + Value=A + Value=1 + Value=1 + Compare=0 + Compare=1 + Compare=0 + Compare=1 + Flags=00000011 +end +item: Custom Dialog Set + Name=Welcome + Display Variable=DISPLAY + item: Dialog + Title=Welcome + Title French=Bienvenue + Title German=Willkommen + Title Portuguese=Bem-vindo + Title Spanish=Bienvenido + Title Italian=Benvenuto + Title Danish=Velkommen + Title Dutch=Welkom + Title Norwegian=Velkommen + Title Swedish=Välkommen + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=172 185 214 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=&Next > + Text French=&Suivant> + Text German=&Weiter> + Text Portuguese=&Próximo> + Text Spanish=&Siguiente > + Text Italian=&Avanti > + Text Danish=&Næste> + Text Dutch=&Volgende> + Text Norwegian=&Neste> + Text Swedish=&Nästa > + end + item: Push Button + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Annuller + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=91 22 245 118 + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000000000000000000000 + Text=<<>> + end + end +end +item: Custom Dialog Set + Name=Display ReadMe + Display Variable=DISPLAY + item: Dialog + Title=Read Me File + Title French=Fichier Lisez-moi + Title German=Liesmich-Datei + Title Portuguese=Ficheiro Leia-me + Title Spanish=Archivo Léeme + Title Italian=File Leggimi + Title Danish=Vigtigt fil + Title Dutch=Leesmij-bestand + Title Norwegian=Informasjonsfil + Title Swedish=Läs mig-fil + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=172 185 214 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=I &Agree > + Text French=&Suivant> + Text German=&Weiter> + Text Portuguese=&Próximo> + Text Spanish=&Siguiente > + Text Italian=&Avanti > + Text Danish=&Næste> + Text Dutch=&Volgende> + Text Norwegian=&Neste> + Text Swedish=&Nästa > + end + item: Push Button + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Slet + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Editbox + Rectangle=85 11 254 170 + Value=%TEMP%\%READMEFILE% + Help Context=16711681 + Create Flags=01010000101000000000100000000100 + end + end +end +item: Custom Dialog Set + Name=Select Destination Directory + Display Variable=DISPLAY + item: Dialog + Title=Choose Destination Location + Title French=Choisissez la localisation de destination + Title German=Zielpfad wählen + Title Portuguese=Escolher Local de Destino + Title Spanish=Elegir una localización de destino + Title Italian=Scegli Posizione di Destinazione + Title Danish=Vælg destinationsmappe + Title Dutch=Kies doellocatie + Title Norwegian=Velg målplassering + Title Swedish=Välj ställe för installationen + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=172 185 214 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=&Next > + Text French=&Suivant> + Text German=&Weiter> + Text Portuguese=&Próximo> + Text Spanish=&Siguiente > + Text Italian=&Avanti > + Text Danish=&Næste> + Text Dutch=&Volgende> + Text Norwegian=&Neste> + Text Swedish=&Nästa > + end + item: Push Button + Rectangle=130 185 172 199 + Variable=DIRECTION + Value=B + Create Flags=01010000000000010000000000000000 + Flags=0000000000000001 + Text=< &Back + Text French=<&Retour + Text German=<&Zurück + Text Portuguese=<&Retornar + Text Spanish=<&Retroceder + Text Italian=< &Indietro + Text Danish=<&Tilbage + Text Dutch=<&Terug + Text Norwegian=<&Tilbake + Text Swedish=< &Tillbaka + end + item: Push Button + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Annuller + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=90 10 260 122 + Create Flags=01010000000000000000000000000000 + Text=Setup will install %APPTITLE% in the following folder. + Text= + Text=To install into a different folder, click Browse, and select another folder. + Text= + Text=You can choose not to install %APPTITLE% by clicking Cancel to exit Setup. + Text French=%APPTITLE% va être installé dans le répertoire ci-dessous + Text French= + Text French=Pour l'installer dans un répertoire différent, cliquez sur Parcourir et sélectionnez un autre répertoire + Text French= + Text French=Vous pouvez choisir de ne pas installer %APPTITLE% en cliquant sur Annuler pour quitter l'Installation + Text German=Installation speichert %APPTITLE% im unten angegebenen Ordner: + Text German= + Text German=Zur Installation in einem anderen Ordner auf Blättern klicken und einen anderen Ordner wählen. + Text German= + Text German=Wenn Sie %APPTITLE% nicht installieren möchten, können Sie durch Klicken auf Abbrechen die Installation beenden. + Text Portuguese=Configuração instalará %APPTITLE% na seguinte pasta + Text Portuguese= + Text Portuguese=Para instalar numa pasta diferente, faça um clique sobre Procurar, e seleccione uma outra pasta. + Text Portuguese= + Text Portuguese=Pode escolher não instalar %APPTITLE% clicando no botão Cancelar para sair da Configuração + Text Spanish=El programa de Configuración instalará %APPTITLE% en la siguiente carpeta. + Text Spanish= + Text Spanish=Para instalar en una carpeta diferente, haga un clic en Visualizar, y seleccione otra carpeta. + Text Spanish= + Text Spanish=Puede elegir no instalar %APPTITLE% haciendo un clic en Cancelar para salir de Configuración. + Text Italian=Il programma di installazione installerà %APPTITLE% nella seguente cartella. + Text Italian= + Text Italian=Per effettuare l’installazione in una cartella diversa, fai clic su Sfoglia, e scegli un’altra cartella. + Text Italian= + Text Italian=Puoi scegliere di non installare %APPTITLE% facendo clic su Annulla per uscire dal programma di installazione + Text Danish=Installationsprogrammet installerer %APPTITLE% i denne mappe. + Text Danish= + Text Danish=Man installerer i en anden mappe ved at klikke på Browse og vælge en anden mappe. + Text Danish= + Text Danish=Man kan vælge ikke at installere %APPTITLE% ved at klikke på Slet og forlade installationsprogrammet. + Text Dutch=Het installatieprogramma installeert %APPTITLE% in de volgende directory. + Text Dutch= + Text Dutch=Als u het in een andere directory wilt installeren, klik dan op Bladeren en kies een andere locatie. + Text Dutch= + Text Dutch=U kunt ervoor kiezen om %APPTITLE% niet te installeren: klik op Annuleren om het installatieprogramma te verlaten. + Text Norwegian=Oppsett vil installere %APPTITLE% i følgende mappe. + Text Norwegian= + Text Norwegian=For å installere i en annen mappe, klikk Bla igjennom og velg en annen mappe. + Text Norwegian= + Text Norwegian=Du kan velge å ikke installere %APPTITLE% ved å velge Avbryt for å gå ut av Oppsett. + Text Swedish=Installationsprogrammet installerar %APPTITLE% i följande mapp. + Text Swedish= + Text Swedish=Om du vill att installationen ska göras i en annan mapp, klickar du på Bläddra och väljer en annan mapp. + Text Swedish= + Text Swedish=Du kan välja att inte installera %APPTITLE% genom att klicka på Avbryt för att lämna installationsprogrammet. + end + item: Static + Rectangle=90 134 260 162 + Action=1 + Create Flags=01010000000000000000000000000111 + Text=Destination Folder + Text French=Répertoire de destination + Text German=Zielordner + Text Portuguese=Pasta de Destino + Text Spanish=Carpeta de Destino + Text Italian=Cartella di destinazione + Text Danish=Destinationsmappe + Text Dutch=Doeldirectory + Text Norwegian=Målmappe + Text Swedish=Destinationsmapp + end + item: Push Button + Rectangle=213 143 255 157 + Variable=MAINDIR_SAVE + Value=%MAINDIR% + Destination Dialog=1 + Action=2 + Create Flags=01010000000000010000000000000000 + Text=B&rowse... + Text French=P&arcourir + Text German=B&lättern... + Text Portuguese=P&rocurar + Text Spanish=V&isualizar... + Text Italian=Sfoglia... + Text Danish=&Gennemse... + Text Dutch=B&laderen... + Text Norwegian=Bla igjennom + Text Swedish=&Bläddra + end + item: Static + Rectangle=95 146 211 157 + Destination Dialog=2 + Create Flags=01010000000000000000000000000000 + Text=%MAINDIR% + Text French=%MAINDIR% + Text German=%MAINDIR% + Text Portuguese=%MAINDIR% + Text Spanish=%MAINDIR% + Text Italian=%MAINDIR% + Text Danish=%MAINDIR% + Text Dutch=%MAINDIR% + Text Norwegian=%MAINDIR% + Text Swedish=%MAINDIR% + end + end + item: Dialog + Title=Select Destination Directory + Title French=Choisissez le répertoire de destination + Title German=Zielverzeichnis wählen + Title Portuguese=Seleccionar Directório de Destino + Title Spanish=Seleccione el Directorio de Destino + Title Italian=Seleziona Directory di destinazione + Title Danish=Vælg Destinationsbibliotek + Title Dutch=Kies doeldirectory + Title Norwegian=Velg målkatalog + Title Swedish=Välj destinationskalatog + Width=221 + Height=173 + Font Name=Helv + Font Size=8 + item: Listbox + Rectangle=5 2 160 149 + Variable=MAINDIR + Create Flags=01010000100000010000000101000000 + Flags=0000110000100010 + Text=%MAINDIR% + Text French=%MAINDIR% + Text German=%MAINDIR% + Text Portuguese=%MAINDIR% + Text Spanish=%MAINDIR% + Text Italian=%MAINDIR% + Text Danish=%MAINDIR% + Text Dutch=%MAINDIR% + Text Norwegian=%MAINDIR% + Text Swedish=%MAINDIR% + end + item: Push Button + Rectangle=167 6 212 21 + Create Flags=01010000000000010000000000000001 + Text=OK + Text French=OK + Text German=OK + Text Portuguese=OK + Text Spanish=ACEPTAR + Text Italian=OK + Text Danish=OK + Text Dutch=OK + Text Norwegian=OK + Text Swedish=OK + end + item: Push Button + Rectangle=167 25 212 40 + Variable=MAINDIR + Value=%MAINDIR_SAVE% + Create Flags=01010000000000010000000000000000 + Flags=0000000000000001 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Slet + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + end +end +item: Custom Dialog Set + Name=Select Packages + Display Variable=DISPLAY + item: Dialog + Title=Select Packages + Width=271 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=150 187 195 202 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=&Next > + Text French=&Suite > + Text German=&Weiter > + Text Spanish=&Siguiente > + Text Italian=&Avanti > + end + item: Push Button + Rectangle=105 187 150 202 + Variable=DIRECTION + Value=B + Create Flags=01010000000000010000000000000000 + Text=< &Back + Text French=< &Retour + Text German=< &Zurück + Text Spanish=< &Atrás + Text Italian=< &Indietro + end + item: Push Button + Rectangle=211 187 256 202 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=&Cancel + Text French=&Annuler + Text German=&Abbrechen + Text Spanish=&Cancelar + Text Italian=&Annulla + end + item: Static + Rectangle=8 180 256 181 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=86 8 258 28 + Create Flags=01010000000000000000000000000000 + Flags=0000000000000001 + Name=Times New Roman + Font Style=-24 0 0 0 700 255 0 0 0 3 2 1 18 + Text=Select Packages + Text French=Sélectionner les composants + Text German=Komponenten auswählen + Text Spanish=Seleccione componentes + Text Italian=Selezionare i componenti + end + item: Checkbox + Rectangle=83 62 211 146 + Variable=COMPONENTS LIBS,COMM,OA,OS,PROG,WP,GAMES + Create Flags=01010000000000010000000000000011 + Flags=0000000000000110 + Text=Libraries + Text=Communication + Text=Productivity + Text=Operating System + Text=Programming + Text=Word Processing + Text=Games and Amusements + Text= + end + item: Static + Rectangle=194 162 242 172 + Variable=COMPONENTS, LIBS, COMM, OA, OS, PROG, WP, GAMES + Value=MAINDIR + Create Flags=01010000000000000000000000000010 + end + item: Static + Rectangle=194 153 242 162 + Variable=COMPONENTS, LIBS, COMM, OA, OS, PROG, WP, GAMES + Create Flags=01010000000000000000000000000010 + end + item: Static + Rectangle=107 153 196 164 + Create Flags=01010000000000000000000000000000 + Text=Disk Space Required: + Text French=Espace disque requis : + Text German=Notwendiger Speicherplatz: + Text Spanish=Espacio requerido en el disco: + Text Italian=Spazio su disco necessario: + end + item: Static + Rectangle=107 162 196 172 + Create Flags=01010000000000000000000000000000 + Text=Disk Space Remaining: + Text French=Espace disque disponible : + Text German=Verbleibender Speicherplatz: + Text Spanish=Espacio en disco disponible: + Text Italian=Spazio su disco disponibile: + end + item: Static + Rectangle=80 146 256 175 + Action=1 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=83 30 256 57 + Create Flags=01010000000000000000000000000000 + Text=Choose which package categories to install by checking the boxes below. Press the Options buttons to select individual packages. + Text French=Choisissez les composants que vous voulez installer en cochant les cases ci-dessous. + Text German=Wählen Sie die zu installierenden Komponenten, indem Sie in die entsprechenden Kästchen klicken. + Text Spanish=Elija los componentes que desee instalar marcando los cuadros de abajo. + Text Italian=Scegliere quali componenti installare selezionando le caselle sottostanti. + end + item: Push Button + Rectangle=230 62 254 72 + Variable=LIBS_SAVE + Value=%LIBS% + Destination Dialog=1 + Action=2 + Create Flags=01010000000000010000000000000000 + Text=Options + Text French=&Annuler + Text German=&Abbrechen + Text Spanish=&Cancelar + Text Italian=&Annulla + end + item: Push Button + Rectangle=230 74 254 84 + Variable=COMM_SAVE + Value=%COMM% + Destination Dialog=2 + Action=2 + Create Flags=01010000000000010000000000000000 + Text=Options + Text French=&Annuler + Text German=&Abbrechen + Text Spanish=&Cancelar + Text Italian=&Annulla + end + item: Push Button + Rectangle=230 86 254 96 + Variable=OA_SAVE + Value=%OA% + Destination Dialog=3 + Action=2 + Create Flags=01010000000000010000000000000000 + Text=Options + Text French=&Annuler + Text German=&Abbrechen + Text Spanish=&Cancelar + Text Italian=&Annulla + end + item: Push Button + Rectangle=230 98 254 108 + Variable=OS_SAVE + Value=%OS% + Destination Dialog=4 + Action=2 + Create Flags=01010000000000010000000000000000 + Text=Options + Text French=&Annuler + Text German=&Abbrechen + Text Spanish=&Cancelar + Text Italian=&Annulla + end + item: Push Button + Rectangle=230 110 254 120 + Variable=PROG_SAVE + Value=%PROG% + Destination Dialog=5 + Action=2 + Create Flags=01010000000000010000000000000000 + Text=Options + Text French=&Annuler + Text German=&Abbrechen + Text Spanish=&Cancelar + Text Italian=&Annulla + end + item: Push Button + Rectangle=230 122 254 132 + Variable=WP_SAVE + Value=%WP% + Destination Dialog=6 + Action=2 + Create Flags=01010000000000010000000000000000 + Text=Options + Text French=&Annuler + Text German=&Abbrechen + Text Spanish=&Cancelar + Text Italian=&Annulla + end + item: Push Button + Rectangle=230 134 254 144 + Variable=GAMES_SAVE + Value=%GAMES% + Destination Dialog=7 + Action=2 + Create Flags=01010000000000010000000000000000 + Text=Options + Text French=&Annuler + Text German=&Abbrechen + Text Spanish=&Cancelar + Text Italian=&Annulla + end + item: Set Variable + Variable=COMPONENTS + Value=X + Flags=00000001 + end + end +<<>> +end +item: Custom Dialog Set + Name=Select Program Manager Group + Display Variable=DISPLAY + item: Dialog + Title=Select Program Manager Group + Title French=Sélectionnez le Groupe du Gestionnaire de Programmes + Title German=Programm-Managergruppe wählen + Title Portuguese=Seleccionar o Grupo Gestor de Programas + Title Spanish=Seleccione el Grupo del Administrador del Programa + Title Italian=Seleziona il gruppo Program Manager + Title Danish=Vælg Programstyringsgruppen + Title Dutch=Kies Programmabeheergroep. + Title Norwegian=Velg Programbehandlingsgruppen + Title Swedish=Välj grupp i Programhanteraren + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=172 185 214 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=&Next > + Text French=&Suivant> + Text German=&Weiter> + Text Portuguese=&Próximo> + Text Spanish=&Siguiente > + Text Italian=&Avanti > + Text Danish=&Næste> + Text Dutch=&Volgende> + Text Norwegian=&Neste> + Text Swedish=&Nästa > + end + item: Push Button + Rectangle=130 185 172 199 + Variable=DIRECTION + Value=B + Create Flags=01010000000000010000000000000000 + Flags=0000000000000001 + Text=< &Back + Text French=<&Retour + Text German=<&Zurück + Text Portuguese=<&Retornar + Text Spanish=<&Retroceder + Text Italian=< &Indietro + Text Danish=<&Back + Text Dutch=<&Terug + Text Norwegian=<&Tilbake + Text Swedish=< &Tillbaka + end + item: Push Button + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Slet + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=90 10 260 38 + Create Flags=01010000000000000000000000000000 + Text=Enter the name of the Program Manager group to add %APPTITLE% icons to: + Text French=Entrez le nom du groupe du Gestionnaire de Programmes où placer les icônes %APPTITLE% à : + Text German=Den Namen der Programm-Managergruppe wählen, in der die %APPTITLE%-Symbole gespeichert werden sollen: + Text Portuguese=Introduzir o nome do Grupo Gestor de Programa para acrescentar os ícones %APPTITLE% para: + Text Spanish=Introduzca el nombre del grupo del Administrador del Programa para añadir los iconos %APPTITLE para: + Text Italian=Inserisci il nome del gruppo Program Manager per aggiungere le icone di %APPTITLE% a: + Text Danish=Indtast navnet på Programstyringsgruppen der skal tilføjes %APPTITLE% elementer: + Text Dutch=Breng de naam van de programmabeheergroep in waaraan u %APPTITLE%-pictogrammen wilt toevoegen. + Text Norwegian=Tast inn navnet på programbehandlingsgruppen for å legge %APPTITLE%-ikoner til: + Text Swedish=Skriv in namnet på den grupp i Programhanteraren där du vill ha ikonerna för %APPTITLE%: + end + item: Combobox + Rectangle=90 42 260 148 + Variable=GROUP + Create Flags=01010000001000010000001100000001 + Flags=0000000000000001 + Text=%GROUP% + Text= + Text French=%GROUP% + Text French= + Text German=%GROUP% + Text German= + Text Portuguese=%GROUP% + Text Portuguese= + Text Spanish=%GROUP% + Text Spanish= + Text Italian=%GROUP% + Text Italian= + Text Danish=%GROUP% + Text Danish= + Text Dutch=%GROUP% + Text Dutch= + Text Norwegian=%GROUP% + Text Norwegian= + Text Swedish=%GROUP% + Text Swedish= + end + end +end +item: Custom Dialog Set + Name=Start Installation + Display Variable=DISPLAY + item: Dialog + Title=Start Installation + Title French=Commencer l'installation + Title German=Installation beginnen + Title Portuguese=Iniciar Instalação + Title Spanish=Comenzar la Instalación + Title Italian=Avvia Installazione + Title Danish=Start installationen + Title Dutch=Start de installatie. + Title Norwegian=Start installeringen + Title Swedish=Starta installationen + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=172 185 214 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=&Next > + Text French=&Suivant> + Text German=&Weiter> + Text Portuguese=&Próximo> + Text Spanish=&Siguiente > + Text Italian=&Avanti > + Text Danish=&Næste> + Text Dutch=&Volgende> + Text Norwegian=&Neste> + Text Swedish=&Nästa > + end + item: Push Button + Rectangle=130 185 172 199 + Variable=DIRECTION + Value=B + Create Flags=01010000000000010000000000000000 + Text=< &Back + Text French=<&Retour + Text German=<&Zurück + Text Portuguese=<&Retornar + Text Spanish=<&Retroceder + Text Italian=< &Indietro + Text Danish=<&Tilbage + Text Dutch=<&Terug + Text Norwegian=<&Tilbake + Text Swedish=< &Tillbaka + end + item: Push Button + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Annuller + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=90 10 260 70 + Create Flags=01010000000000000000000000000000 + Text=You are now ready to install %APPTITLE%. + Text= + Text=Press the Next button to begin the installation or the Back button to reenter the installation information. + Text French=Vous êtes maintenant prêt à installer %APPTITLE% + Text French= + Text French=Cliquez sur Suivant pour commencer l'installation ou Retour pour entrer à nouveau les informations d'installation + Text German=Sie sind jetzt zur Installation von %APPTITLE% bereit. + Text German= + Text German=Auf die Schaltfläche Weiter klicken, um mit dem Start der Installation zu beginnen, oder auf die Schaltfläche Zurück, um die Installationsinformationen nochmals aufzurufen. + Text Portuguese=Está agora pronto para instalar %APPTITLE% + Text Portuguese= + Text Portuguese=Pressione o botão Próximo para começar a instalação ou o botão Retornar para introduzir novamente a informação sobre a instalação + Text Spanish=Ahora estará listo para instalar %APPTITLE%. + Text Spanish= + Text Spanish=Pulse el botón de Próximo para comenzar la instalación o el botón Retroceder para volver a introducir la información sobre la instalación. + Text Italian=Sei pronto ad installare %APPTITLE%. + Text Italian= + Text Italian=Premi il tasto Avanti per iniziare l’installazione o il tasto Indietro per rientrare nuovamente nei dati sull’installazione + Text Danish=Du er nu klar til at installere %APPTITLE%. + Text Danish= + Text Danish=Klik på Næste for at starte installationen eller på Tilbage for at ændre installationsoplysningerne. + Text Dutch=U bent nu klaar om %APPTITLE% te installeren. + Text Dutch= + Text Dutch=Druk op Volgende om met de installatie te beginnen of op Terug om de installatie-informatie opnieuw in te voeren. + Text Norwegian=Du er nå klar til å installere %APPTITLE% + Text Norwegian= + Text Norwegian=Trykk på Neste-tasten for å starte installeringen, eller Tilbake-tasten for å taste inn installasjonsinformasjonen på nytt. + Text Swedish=Du är nu redo att installera %APPTITLE%. + Text Swedish= + Text Swedish=Tryck på Nästa för att starta installationen eller på Tillbaka för att skriva in installationsinformationen på nytt. + end + end +end +item: If/While Statement + Variable=DISPLAY + Value=Select Destination Directory +end +item: Set Variable + Variable=BACKUP + Value=%MAINDIR%\BACKUP +end +item: End Block +end +item: End Block +end +item: If/While Statement + Variable=DOBACKUP + Value=A +end +item: Set Variable + Variable=BACKUPDIR + Value=%BACKUP% +end +item: End Block +end +item: Open/Close INSTALL.LOG +end +item: Check Disk Space + Component=COMPONENTS +end +item: Display Graphic + Pathname=<<>>\nt\Wise\xemacs-beta.bmp + X Position=32784 + Y Position=16 +end +item: Include Script + Pathname=%_WISE_%\INCLUDE\uninstal.wse +end +<<>> +<<>> +<<>> +<<>> +item: Set Variable + Variable=COMMON + Value=%COMMON% + Flags=00010100 +end +item: Set Variable + Variable=MAINDIR + Value=%MAINDIR% + Flags=00010100 +end +item: Check Configuration + Flags=10111011 +end +item: Get Registry Key Value + Variable=STARTUPDIR + Key=Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders + Default=%WIN%\Start Menu\Programs\StartUp + Value Name=StartUp + Flags=00000010 +end +item: Get Registry Key Value + Variable=DESKTOPDIR + Key=Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders + Default=%WIN%\Desktop + Value Name=Desktop + Flags=00000010 +end +item: Get Registry Key Value + Variable=STARTMENUDIR + Key=Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders + Default=%WIN%\Start Menu + Value Name=Start Menu + Flags=00000010 +end +item: Get Registry Key Value + Variable=GROUPDIR + Key=Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders + Default=%WIN%\Start Menu\Programs + Value Name=Programs + Flags=00000010 +end +item: Get Registry Key Value + Variable=CSTARTUPDIR + Key=Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders + Default=%STARTUPDIR% + Value Name=Common Startup + Flags=00000100 +end +item: Get Registry Key Value + Variable=CDESKTOPDIR + Key=Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders + Default=%DESKTOPDIR% + Value Name=Common Desktop + Flags=00000100 +end +item: Get Registry Key Value + Variable=CSTARTMENUDIR + Key=Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders + Default=%STARTMENUDIR% + Value Name=Common Start Menu + Flags=00000100 +end +item: Get Registry Key Value + Variable=CGROUPDIR + Key=Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders + Default=%GROUPDIR% + Value Name=Common Programs + Flags=00000100 +end +item: Set Variable + Variable=CGROUP_SAVE + Value=%GROUP% +end +item: Set Variable + Variable=GROUP + Value=%GROUPDIR%\%GROUP% +end +item: Create Shortcut + Source=%MAINDIR%\<<>>\i386-pc-win32\runemacs.exe + Destination=%GROUP%\XEmacs.lnk + Working Directory=\ + Icon Number=0 +end +item: Create Shortcut + Source=%MAINDIR%\<<>>\i386-pc-win32\runemacs.exe + Destination=%DESKTOPDIR%\XEmacs.lnk + Working Directory=\ + Icon Number=0 +end +item: Else Statement +end +item: Add ProgMan Icon + Group=%GROUP% + Icon Name=XEmacs + Command Line=%MAINDIR%\<<>>\i386-pc-win32\runemacs.exe + Default Directory=\ + Flags=01000000 +end +item: End Block +end +item: Edit Registry + Total Keys=16 + item: Key + Key=SOFTWARE\GNU\XEmacs + New Value=%MAINDIR% + Value Name=emacs_dir + Root=2 + end + item: Key + Key=SOFTWARE\GNU\XEmacs + New Value=%MAINDIR%\xemacs-packages + Value Name=EMACSPACKAGEPATH + Root=2 + end + item: Key + Key=SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\runemacs.exe + New Value=%MAINDIR%\<<>>\i386-pc-win32 + Value Name=Path + Root=2 + end + item: Key + Key=SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\xemacs.exe + New Value=%MAINDIR%\<<>>\i386-pc-win32 + Value Name=Path + Root=2 + end + item: Key + Key=.el + New Value=elfile + end + item: Key + Key=.el + New Value=text/plain + Value Name=Content Type + end + item: Key + Key=elfile + New Value=Emacs lisp + end + item: Key + Key=elfile + New Value=00 00 01 00 + Value Name=EditFlags + Data Type=4 + end + item: Key + Key=elfile\DefaultIcon + New Value=%MAINDIR%\<<>>\i386-pc-win32\runemacs.exe,2 + end + item: Key + Key=elfile\QuickView + New Value=* + end + item: Key + Key=elfile\Shell + New Value= + end + item: Key + Key=elfile\Shell\open + end + item: Key + Key=elfile\Shell\open\command + New Value=%MAINDIR%\<<>>\i386-pc-win32\runemacs.exe "%%1" + end + item: Key + Key=elfile\Shell\open\ddeexec + New Value=open("%%1") + end + item: Key + Key=elfile\Shell\open\ddeexec\Application + New Value=XEmacs + New Value= + end + item: Key + Key=elfile\Shell\open\ddeexec\topic + New Value=System + end +end +item: Wizard Block + Direction Variable=DIRECTION + Display Variable=DISPLAY + Bitmap Pathname=<<>>\nt\Wise\gnu.bmp + X Position=9 + Y Position=10 + Filler Color=8421440 + Flags=00000011 +end +item: Custom Dialog Set + Name=Finished + Display Variable=DISPLAY + item: Dialog + Title=Installation Complete + Title French=Installation en cours + Title German=Installation abgeschlossen + Title Portuguese=Instalação Completa + Title Spanish=Se ha completado la Instalación + Title Italian=Installazione completata + Title Danish=Installation gennemført + Title Dutch=Installatie afgerond + Title Norwegian=Installasjonen er fullført + Title Swedish=Installationen klar + Width=280 + Height=224 + Font Name=Helv + Font Size=8 + item: Push Button + Rectangle=170 185 212 199 + Variable=DIRECTION + Value=N + Create Flags=01010000000000010000000000000001 + Text=&Finish > + Text French=&Terminer> + Text German=&Fertigstellen> + Text Portuguese=&Terminar > + Text Spanish=&Finalizar> + Text Italian=&Fine > + Text Danish=&Afslut > + Text Dutch=&Klaar> + Text Norwegian=&Avslutt> + Text Swedish=&Sluta> + end + item: Push Button + Control Name=CANCEL + Rectangle=222 185 264 199 + Action=3 + Create Flags=01010000000000010000000000000000 + Text=Cancel + Text French=Annuler + Text German=Abbrechen + Text Portuguese=Cancelar + Text Spanish=Cancelar + Text Italian=Annulla + Text Danish=Annuller + Text Dutch=Annuleren + Text Norwegian=Avbryt + Text Swedish=Avbryt + end + item: Static + Rectangle=9 177 263 178 + Action=3 + Create Flags=01010000000000000000000000000111 + end + item: Static + Rectangle=90 10 260 63 + Enabled Color=00000000000000001111111111111111 + Create Flags=01010000000000000000000000000000 + Text=%APPTITLE% has been successfully installed. + Text= + Text= + Text=Press the Finish button to exit this installation. + Text= + Text French=L'installation de %APPTITLE% est réussie + Text French= + Text French= + Text French=Cliquez sur Terminer pour quitter cette installation + Text French= + Text German=%APPTITLE% wurde erfolgreich installiert. + Text German= + Text German= + Text German=Zum Beenden dieser Installation Fertigstellen anklicken. + Text German= + Text Portuguese=%APPTITLE% foi instalado com êxito + Text Portuguese= + Text Portuguese= + Text Portuguese=Pressionar o botão Terminar para sair desta instalação + Text Portuguese= + Text Spanish=%APPTITLE% se ha instalado con éxito. + Text Spanish= + Text Spanish= + Text Spanish=Pulse el botón de Finalizar para salir de esta instalación. + Text Spanish= + Text Italian=%APPTITLE% è stato installato. + Text Italian= + Text Italian= + Text Italian=Premi il pulsante Fine per uscire dal programma di installazione + Text Italian= + Text Danish=%APPTITLE% er nu installeret korrekt. + Text Danish= + Text Danish= + Text Danish=Klik på Afslut for at afslutte installationen. + Text Danish= + Text Dutch=%APPTITLE% is met succes geïnstalleerd. + Text Dutch= + Text Dutch= + Text Dutch=Druk op Klaar om deze installatie af te ronden. + Text Dutch= + Text Norwegian=Installasjonen av %APPTITLE% er suksessfull. + Text Norwegian= + Text Norwegian= + Text Norwegian=Trykk på Avslutt-tasten for å avslutte denne installasjonen. + Text Norwegian= + Text Swedish=Installationen av %APPTITLE% har lyckats. + Text Swedish= + Text Swedish= + Text Swedish=Tryck på Sluta för att gå ur installationsprogrammet. + Text Swedish= + end + item: Push Button + Control Name=BACK + Rectangle=128 185 170 199 + Variable=DIRECTION + Value=B + Create Flags=01010000000000010000000000000000 + Text=< &Back + Text French=<&Retour + Text German=<&Zurück + Text Portuguese=<&Retornar + Text Spanish=<&Retroceder + Text Italian=< &Indietro + Text Danish=<&Tilbage + Text Dutch=<&Terug + Text Norwegian=<&Tilbake + Text Swedish=< &Tillbaka + end + item: Set Control Attribute + Control Name=BACK + Operation=1 + end + item: Set Control Attribute + Control Name=CANCEL + Operation=1 + end + end +end +item: End Block +end +item: New Event + Name=Cancel +end +item: Include Script + Pathname=%_WISE_%\INCLUDE\rollback.wse +end diff -r 28d9c139be4c -r 11054d720c21 nt/xemacs.mak --- a/nt/xemacs.mak Mon Aug 13 11:25:03 2007 +0200 +++ b/nt/xemacs.mak Mon Aug 13 11:26:11 2007 +0200 @@ -30,6 +30,9 @@ NT=$(XEMACS)\nt OUTDIR=$(NT)\obj +# Define a variable for the 'del' command to use +DEL=-del + # Program name and version !include "..\version.sh" @@ -117,6 +120,9 @@ !if !defined(HAVE_NATIVE_SOUND) HAVE_NATIVE_SOUND=1 !endif +!if !defined(HAVE_WIDGETS) +HAVE_WIDGETS=1 +!endif !if !defined(DEBUG_XEMACS) DEBUG_XEMACS=0 !endif @@ -311,6 +317,9 @@ MSW_DIALOG_SRC=$(XEMACS)\src\dialog.c $(XEMACS)\src\dialog-msw.c MSW_DIALOG_OBJ=$(OUTDIR)\dialog.obj $(OUTDIR)\dialog-msw.obj !endif +!if $(HAVE_WIDGETS) +MSW_DEFINES=$(MSW_DEFINES) -DHAVE_WIDGETS +!endif !if $(HAVE_NATIVE_SOUND) MSW_DEFINES=$(MSW_DEFINES) -DHAVE_NATIVE_SOUND !endif @@ -881,7 +890,7 @@ !if $(DEBUG_XEMACS) @dir /b/s $(OUTDIR)\*.sbr > bscmake.tmp bscmake -nologo -o$(TEMACS_BROWSE) @bscmake.tmp - @del bscmake.tmp + @$(DEL) bscmake.tmp !endif link.exe @<< $(TEMACS_LFLAGS) $(TEMACS_OBJS) $(TEMACS_LIBS) @@ -981,7 +990,7 @@ $(MANDIR)\xemacs\text.texi \ $(MANDIR)\xemacs\trouble.texi \ $(MANDIR)\xemacs\undo.texi \ - $(MANDIR)\xemacs\windows.texi \ + $(MANDIR)\xemacs\windows.texi $(INFODIR)\lispref.info: $(MANDIR)\lispref\lispref.texi @@ -1016,7 +1025,8 @@ $(MANDIR)\lispref\hash-tables.texi \ $(MANDIR)\lispref\help.texi \ $(MANDIR)\lispref\hooks.texi \ - $(MANDIR)\lispref\index.texi \ + $(MANDIR)\lispref\index.perm \ + $(MANDIR)\lispref\index.unperm \ $(MANDIR)\lispref\internationalization.texi \ $(MANDIR)\lispref\intro.texi \ $(MANDIR)\lispref\keymaps.texi \ @@ -1054,7 +1064,7 @@ $(MANDIR)\lispref\windows.texi \ $(MANDIR)\lispref\x-windows.texi \ $(MANDIR)\lispref\index.unperm \ - $(MANDIR)\lispref\index.perm \ + $(MANDIR)\lispref\index.perm $(INFODIR)\new-users-guide.info: $(MANDIR)\new-users-guide\new-users-guide.texi @@ -1070,7 +1080,7 @@ $(MANDIR)\new-users-guide\edit.texi \ $(MANDIR)\new-users-guide\modes.texi \ $(MANDIR)\new-users-guide\xmenu.texi \ - $(MANDIR)\new-users-guide\enter.texi \ + $(MANDIR)\new-users-guide\enter.texi $(INFODIR)\internals.info: $(MANDIR)\internals\internals.texi @@ -1079,7 +1089,7 @@ $(MANDIR)\internals\internals.texi: \ $(MANDIR)\internals\index.unperm \ - $(MANDIR)\internals\index.perm \ + $(MANDIR)\internals\index.perm info: $(INFO_FILES) @@ -1093,7 +1103,7 @@ LOADPATH=$(LISP) $(DOC): $(LIB_SRC)\make-docfile.exe - -del $(DOC) + $(DEL) $(DOC) $(TEMACS) -batch -l $(TEMACS_DIR)\..\lisp\make-docfile.el -- -o $(DOC) -i $(XEMACS)\site-packages $(LIB_SRC)\make-docfile.exe -a $(DOC) -d $(TEMACS_SRC) $(DOC_SRC1) $(LIB_SRC)\make-docfile.exe -a $(DOC) -d $(TEMACS_SRC) $(DOC_SRC2) @@ -1123,8 +1133,9 @@ #------------------------------------------------------------------------------ # use this rule to build the complete system -all: $(XEMACS)\Installation $(OUTDIR)\nul $(LASTFILE) $(LWLIB) $(LIB_SRC_TOOLS) $(RUNEMACS) \ - $(TEMACS) update-elc $(DOC) dump-xemacs info +all: $(XEMACS)\Installation $(OUTDIR)\nul $(LASTFILE) $(LWLIB) \ + $(LIB_SRC_TOOLS) $(RUNEMACS) $(TEMACS) update-elc $(DOC) dump-xemacs \ + $(LISP)/auto-autoloads.el $(LISP)/custom-load.el info temacs: $(TEMACS) @@ -1134,7 +1145,7 @@ @echo PlaceHolder > PlaceHolder @xcopy /q PROBLEMS "$(INSTALL_DIR)\" @xcopy /q PlaceHolder "$(INSTALL_DIR)\lock\" - @del "$(INSTALL_DIR)\lock\PlaceHolder" + @$(DEL) "$(INSTALL_DIR)\lock\PlaceHolder" @xcopy /q $(LIB_SRC)\*.exe "$(INSTALL_DIR)\$(EMACS_CONFIGURATION)\" @copy $(LIB_SRC)\DOC "$(INSTALL_DIR)\$(EMACS_CONFIGURATION)" @copy $(CONFIG_VALUES) "$(INSTALL_DIR)\$(EMACS_CONFIGURATION)" @@ -1145,50 +1156,50 @@ @xcopy /e /q $(XEMACS)\lisp "$(INSTALL_DIR)\lisp\" @echo Making skeleton package tree in $(PACKAGE_PREFIX) ... @xcopy /q PlaceHolder "$(PACKAGE_PREFIX)\site-packages\" - @del "$(PACKAGE_PREFIX)\site-packages\PlaceHolder" + @$(DEL) "$(PACKAGE_PREFIX)\site-packages\PlaceHolder" @xcopy /q PlaceHolder "$(PACKAGE_PREFIX)\mule-packages\" - @del "$(PACKAGE_PREFIX)\mule-packages\PlaceHolder" + @$(DEL) "$(PACKAGE_PREFIX)\mule-packages\PlaceHolder" @xcopy /q PlaceHolder "$(PACKAGE_PREFIX)\xemacs-packages\" - @del "$(PACKAGE_PREFIX)\xemacs-packages\PlaceHolder" - @del PlaceHolder + @$(DEL) "$(PACKAGE_PREFIX)\xemacs-packages\PlaceHolder" + @$(DEL) PlaceHolder distclean: - del *.bak - del *.orig - del *.rej - del *.tmp - del $(XEMACS)\Installation + $(DEL) *.bak + $(DEL) *.orig + $(DEL) *.rej + $(DEL) *.tmp + $(DEL) $(XEMACS)\Installation cd $(OUTDIR) - del *.lib - del *.obj - del *.pdb - del *.res - del *.sbr + $(DEL) *.lib + $(DEL) *.obj + $(DEL) *.pdb + $(DEL) *.res + $(DEL) *.sbr cd $(XEMACS)\$(TEMACS_DIR) - del config.h - del paths.h - del Emacs.ad.h - del *.bak - del *.orig - del *.rej - del *.exe - del *.map - del *.bsc - del *.pdb + $(DEL) config.h + $(DEL) paths.h + $(DEL) Emacs.ad.h + $(DEL) *.bak + $(DEL) *.orig + $(DEL) *.rej + $(DEL) *.exe + $(DEL) *.map + $(DEL) *.bsc + $(DEL) *.pdb cd $(LIB_SRC) - del DOC - del *.bak - del *.orig - del *.rej - del *.exe - del *.obj - del *.pdb - del *.res - del $(CONFIG_VALUES) + $(DEL) DOC + $(DEL) *.bak + $(DEL) *.orig + $(DEL) *.rej + $(DEL) *.exe + $(DEL) *.obj + $(DEL) *.pdb + $(DEL) *.res + $(DEL) $(CONFIG_VALUES) cd $(LISP) - -del /s /q *.bak *.elc *.orig *.rej + $(DEL) /s /q *.bak *.elc *.orig *.rej cd $(INFODIR) - del *.info* $(MANDIR)\internals\index.texi $(MANDIR)\lispref\index.texi + $(DEL) *.info* $(MANDIR)\internals\index.texi $(MANDIR)\lispref\index.texi depend: mkdepend -f xemacs.mak -p$(OUTDIR)\ -o.obj -w9999 -- $(TEMACS_CPP_FLAGS) -- $(DOC_SRC1) $(DOC_SRC2) $(DOC_SRC3) $(DOC_SRC4) $(DOC_SRC5) $(DOC_SRC6) $(DOC_SRC7) $(DOC_SRC8) $(DOC_SRC9) $(LASTFILE_SRC)\lastfile.c $(LIB_SRC)\make-docfile.c $(LIB_SRC)\run.c @@ -1257,6 +1268,9 @@ !if $(HAVE_DIALOGS) Compiling in support for dialogs. !endif +!if $(HAVE_WIDGETS) + Compiling in support for widgets. +!endif !if $(HAVE_NATIVE_SOUND) Compiling in support for native sounds. !endif @@ -1286,5 +1300,20 @@ @type $(XEMACS)\Installation @echo -------------------------------------------------------------------- +# Update auto-autoloads.el and custom-load.el similar to what +# XEmacs.rules does for xemacs-packages. +VANILLA=-vanilla +FORCE: +$(LISP)\auto-autoloads.el: FORCE + $(PROGNAME) $(VANILLA) -batch \ + -l autoload -f batch-update-directory $(LISP) + $(PROGNAME) $(VANILLA) -batch \ + -f batch-byte-compile $@ + @$(DEL) $(LISP)\auto-autoloads.el~ + +$(LISP)\custom-load.el: FORCE + $(PROGNAME) $(VANILLA) -batch -l cus-dep \ + -f Custom-make-dependencies $(LISP) + # DO NOT DELETE THIS LINE -- make depend depends on it. diff -r 28d9c139be4c -r 11054d720c21 src/.cvsignore --- a/src/.cvsignore Mon Aug 13 11:25:03 2007 +0200 +++ b/src/.cvsignore Mon Aug 13 11:26:11 2007 +0200 @@ -10,3 +10,4 @@ xemacs SATISFIED update-elc.stamp +*.so.* \ No newline at end of file diff -r 28d9c139be4c -r 11054d720c21 src/ChangeLog --- a/src/ChangeLog Mon Aug 13 11:25:03 2007 +0200 +++ b/src/ChangeLog Mon Aug 13 11:26:11 2007 +0200 @@ -1,10 +1,1873 @@ +1999-11-10 XEmacs Build Bot + + * XEmacs 21.2.20 is released + +1999-11-04 Martin Buchholz + + * mule-ccl.c (ccl_driver): Warning suppression + +1999-11-01 SL Baur + + * emacs.c (main_1): Guard call to reinit_vars_of_debug when not + building a debugged XEmacs. + +1999-10-28 Andreas Jaeger + + * src/emacs.c (main_1): Don't set the malloc hooks if using + DOUG_LEA_MALLOC. + +1999-10-30 Olivier Galibert + + * alloc.c (pdump_dump_rtables): Don't forget to dump the last + registered type. + (pdump): Ditto. + +1999-10-25 Olivier Galibert + + * emacs.c (main_1): Call reinit_vars_of_scrollbar_x. + + * symsinit.h: Declare reinit_vars_of_scrollbar_x. + +1999-10-25 Martin Buchholz + + * redisplay.h (CLASS_RESET_CHANGED_FLAGS): + (GLOBAL_RESET_CHANGED_FLAGS): + (CLASS_REDISPLAY_FLAGS_CHANGEDP): + (RESET_CHANGED_SET_FLAGS): + Fix C++ compile errors/warnings. + These macros were just a tad too clever. + + * process-unix.c (unix_open_network_stream): + * objects-x.c (allocate_nearest_color): + * mule-charset.c (vars_of_mule_charset): + * fileio.c (Ffile_truename): + * file-coding.c (vars_of_file_coding): + Fix compile errors/warnings. + + * alloc.c (xstrdup): Use fact that memcpy returns its first arg. + (allocate_lisp_storage): Simplify. + +1999-10-24 Olivier Galibert + + * conslots.h: Add defines with first and last slot names. + * bufslots.h: Add defines with first and last slot names. + + * buffer.c (common_init_complex_vars_of_buffer): Renamed from + reinit_complex_vars_of_buffer + (reinit_complex_vars_of_buffer): Reset the slots to the dumped + value. + (complex_vars_of_buffer): Dump the slots values. + + * console.c (common_init_complex_vars_of_console): Renamed from + reinit_complex_vars_of_console + (reinit_complex_vars_of_console): Reset the slots to the dumped + value. + (complex_vars_of_console): Dump the slots values. + + * alloc.c: Rename reloc_table to pdump_reloc_table, rt_list to + pdump_rt_list and move them at the beginning of the file. + (gc_sweep): Unmark pdumped objects after the sweep phase. + (pdump_dump_rtables): Change a bare 256 to + last_lrecord_type_index_assigned. Add a separator between the + adresses or lrecords and the ones of C structs in the dump file. + (pdump_load): Cope with the new separator and the renamings. Stop + looking for the hash tables list after it has been found (duh!). + +1999-10-24 Robert Bihlmeyer + + * sound.c: support HAVE_ESD_SOUND + + * miscplay.c: + * miscplay.h: + * linuxplay.c: Move large part of linuxplay to generalized file + miscplay. Make it platform independent. + + * esd.c: New file + +1999-10-24 Adrian Aichner + + * lisp.h (Dynarr_declare): Fix boo-boo. + +1999-10-24 Olivier Galibert + + * process-unix.c (allocate_pty): Fix HAVE_GETPT. + * process.h: Ditto. + +1999-10-24 Jan Vroonhof + + * redisplay.c (start_with_line_at_pixpos): Remove assert(cur_elt + >=0). Handle the cur_elt == 0 case. + +1999-10-24 Jan Vroonhof + + * unexelf.c: Merge Martin's c++ fixes back in + +1999-10-20 Jan Vroonhof + + * unexelf.c (unexec): Only copy the global offset + table from memory on sgi machines. + +1999-08-13 Alexandre Oliva , Vin Shelton + + * unexelf.c: Enable GNU/Linux/alpha to build with gcc 2.95 by + adding support for an sbss section. Get IRIX 5.2 to build using + unexelf.c. + + * m/iris4d.h: Use unexelf.o for unexec. + + * m/iris5d.h: Use unexelf.o for unexec. + +1999-10-24 Jan Vroonhof + + * unexelf.c: Revert to 21.1 version + +1999-08-28 Jan Vroonhof + + * window.c (Fwindow_truncated_p): New function. + +1999-08-25 Jonathan Marten + + * window.c (window_truncation_on): Always return 0 for minibuffer + windows, to enable auto scrolling. + +1999-10-24 Neal Becker + * process.h: Unix98 PTY support + +1999-10-17 Jan Vroonhof + + * fileio.c (Ffile_truename): Do proper mule decoding on + the argument to xrealpath() + +1999-08-19 Stephen Tse + + * process-unix.c (unix_open_network_stream): Add udp network + support; rename variable Qtcpip to Qtcp, parameter family to + protocol for consistency with Qudp. + + * process-nt.c (nt_open_network_stream): Rename variable Qtcpip to + Qtcp, parameter family to protocol for consistency with Qudp. + + * process.c (global_variables): Add a new variable Qudp for udp + network support; rename variable Qtcpip to Qtcp for consistency + with Qudp. + (Fopen_network_stream_internal): Rename parameter FAMILY to + PROTOCOL for consistency; fix a minor typo and add an explanation + in docstring for udp programming. + (Fopen_multicast_group_internal): Fix a minor typo in docstring. + (syms_of_process): Add a new variable Qudp for udp network + support; rename variable Qtcpip to Qtcp for consistency with Qudp. + + * process.h (extern_variables): Add a new variable Qudp for udp + network support; rename variable Qtcpip to Qtcp for consistency + with Qudp. + + * procimpl.h: Add a new variable Qudp for udp network support; + rename variable Qtcpip to Qtcp for consistency with Qudp. + (struct process_methods): Rename parameter family to protocol. + + +1999-10-24 Olivier Galibert + + * alloc.c (pdump_make_hash): Divide pointers by 8 for a better hash. + +1999-10-23 Olivier Galibert + + * lrecord.h (struct lrecord_header): Removed dumped flags. + + * dynarr.c: Use DUMPEDP instead of dumped flag. + + * lisp.h (DUMPEDP): Added. Removed dumped flag from dynarr. + + * alloc.c: Removed hash_next linked list pointer. + + * *.c *.h: Removed markobj and mark_object parameters, removed GC_ + and XGC macros. + +1999-10-14 Andy Piper + + * redisplay-x.c (x_output_shadows): fix dodgy maths for border + calculations. + + * gutter.c (output_gutter): be more accurate about the area to be + cleared since X seems to manage to do the clear after drawing the + border. + + * redisplay.h (RESET_CHANGED_FLAGS): new macro for setting + redisplay flags as a group. + (RESET_CHANGED_SET_FLAGS): ditto. + (CLASS_RESET_CHANGED_FLAGS): ditto. + (GLOBAL_RESET_CHANGED_FLAGS): ditto. + (REDISPLAY_FLAGS_CHANGEDP): new macro for testing redisplay flags + as a group. + (CLASS_REDISPLAY_FLAGS_CHANGEDP): ditto. + (GLOBAL_REDISPLAY_FLAGS_CHANGEDP): ditto. + + * redisplay.c (redisplay_frame): use CLASS_RESET_CHANGED_FLAGS + instead of setting flags individually. + (redisplay_device): ditto CLASS_REDISPLAY_FLAGS_CHANGEDP. + (redisplay_device): ditto. + (redisplay_device): ditto CLASS_RESET_CHANGED_FLAGS. + (redisplay_without_hooks): ditto GLOBAL_REDISPLAY_FLAGS_CHANGEDP. + (redisplay_without_hooks): ditto CLASS_REDISPLAY_FLAGS_CHANGEDP. + (redisplay_without_hooks): ditto. + (redisplay_without_hooks): ditto GLOBAL_RESET_CHANGED_FLAGS. + + * redisplay-x.c (x_output_string): unmap subwindows in the area. + (x_output_blank): ditto. + + * redisplay-output.c (redisplay_output_display_block): don't unmap + subwindows in case layout optimization can avoid it. + (redisplay_output_subwindow): unmap subwindows in the area. + (redisplay_output_layout): optimize the output of layouts - only + output glyphs that have changed if nothing else of redisplay + significance has occurred. + (redisplay_output_pixmap): change args to + redisplay_clear_clipped_region. + (redisplay_clear_clipped_region): allow the clipped region to be + cleared of all subwindows except the one passed in. + + * redisplay-msw.c (mswindows_output_blank): unmap subwindows in + the area. + (mswindows_output_cursor): ditto. + (mswindows_output_string): ditto. + + * gutter.c (calculate_gutter_size): if the window buffer is nil + then don't continue. + (update_frame_gutters): be more lenient about when we actually + update the gutter. Layout optimization makes this + non-costly. Cache redisplay flags that we want to temporarily + ignore. + + * glyphs.c (Fglyph_animated_timeout_handler): handle image + specific timeouts rather than iterating over the instance cache. + (glyph_animated_timeout_mapper): deleted. + (add_glyph_animated_timeout): use a weak list to hold onto the + image so that it can be GC'ed. + (disable_glyph_animated_timeout): disable a specific timeout. + (vars_of_glyphs): disable-animated-pixmaps is a new boolean for + controlling whether pixmaps are animated or not. + + * glyphs-msw.c (mswindows_finalize_image_instance): make sure the + image timeout gets disabled when the image gets freed. + + * glyphs-eimage.c (gif_instantiate): remove meaningless + comment. Cope with timeouts specified in the gif extension block. + + * event-msw.c (vars_of_event_mswindows): new variable + mswindows-meta-activates-menu. + (mswindows_wnd_proc): only goto defproc with VK_MENU if the user + wants it. + + * glyphs-x.c (x_finalize_image_instance): delete mask first so + that we can compare with image. + +1999-10-14 Jonathan Harris + + * event-msw.c (mswindows_key_to_emacs_keysym): + Recognise keypad keys as different from normal keys. + +1999-10-14 Didier Verna + + * glyphs-x.c (x_finalize_image_instance): avoid freeing null pixmaps. + +1999-10-10 Olivier Galibert + + * symbols.c (init_symbols_once_early): dump Vquit_flag. + + * symsinit.h: Updated. + + * ntproc.c (vars_of_ntproc): Use defsymbol. + + * emacs.c (main_1): Updated reinit calls. + + * lisp.h: Removed Fpurecopy and pure_put declarations. + * fns.c: Removed pure_put. + + * eval.c (Fdefvar): pure_put -> Fput + (Fdefconst): Ditto. + * frame-x.c (init_x_prop_symbols): Ditto. + * symbols.c (deferror): Ditto. + + * alloc.c (Fmake_byte_code): Remove Fpurecopy call. + * buffer.c (vars_of_buffer): Ditto. + * bytecode.c (Ffetch_bytecode): Ditto. + (optimize_compiled_function): Ditto. + * emacs.c (vars_of_emacs): Ditto. + * emodules.c (vars_of_module): Ditto. + * eval.c (define_function): Ditto. + (Fautoload): Ditto. + * frame.c (vars_of_frame): Ditto. + * intl.c (Fset_domain): Ditto. + * lread.c (load_force_doc_string_unwind): Ditto. + * menubar.c (vars_of_menubar): Ditto. + * minibuf.c (reinit_complex_vars_of_minibuf): Ditto. + + * debug.c (reinit_vars_of_debug): Extracted. + * device-x.c (reinit_vars_of_device_x): Ditto. + * emodules.c (reinit_vars_of_module): Ditto. + * font-lock.c (reinit_vars_of_font_lock): Ditto. + * glyphs-widget.c (reinit_vars_of_glyphs_widget): Ditto. + * glyphs.c (reinit_vars_of_glyphs): Ditto. + * gui-x.c (reinit_vars_of_gui_x): Ditto. + * insdel.c (reinit_vars_of_insdel): Ditto. + * menubar-x.c (reinit_vars_of_menubar_x): Ditto. + * minibuf.c (reinit_complex_vars_of_minibuf): Ditto. + * mule-wnnfns.c (reinit_vars_of_mule_wnn): Ditto. + * print.c (reinit_vars_of_print): Ditto. + * redisplay.c (reinit_vars_of_redisplay): Ditto. + * select-x.c (reinit_vars_of_xselect): Ditto. + * undo.c (reinit_vars_of_undo): Ditto. + +1999-10-10 Olivier Galibert + + * symsinit.h: Updated declarations, see other ChangeLog entries. + + * redisplay.c (init_redisplay): Ensure proper reinitialisation. + + * lrecord.h (XD_DYNARR_DESC): Introduce XD_INT_RESET and use it. + + * glyphs.c: Add the ii_keyword_entry and related descriptions. + Fix the image_instantiator_methods one. + + * file-coding.c: Plonk all data that needs to be dumped in a + dynamically allocated structure. + + * extents.c (reinit_vars_of_extents): Extracted from + vars_of_extents. + + * event-stream.c (vars_of_event_stream): Don't staticpro when + pdump_wire is enough. + + * event-msw.c (reinit_vars_of_event_mswindows): Extracted from + vars_of_event_mswindows. + + * event-Xt.c (reinit_vars_of_event_Xt): Extracted from + vars_of_event_Xt. + + * eval.c (vars_of_eval): Don't staticpro when pdump_wire is enough. + + * emacs.c (main_1): Added some reinit calls. + + * device-x.c (reinit_console_type_create_device_x): Extracted from + console_type_create_device_x. + + * console.h: Declare the console_type_entry_dynarr description. + + * console.c: Unstatic the console_type_entry_dynarr description. + + * alloc.c: Removed some dubious comments. Handle XD_INT_RESET. + +1999-10-07 Olivier Galibert + + * symsinit.h: Updated declarations, see other ChangeLog entries. + + * minibuf.c (reinit_complex_vars_of_minibuf): Extracted from + complex_vars_of_minibuf. + + * lrecord.h: Removed XD_PARENT_INDIRECT (unused and + unimplemented), added XD_LO_LINK. + + * lisp.h (pdump_wire_list): Add declaration. + + * glyphs.h (INITIALIZE_DEVICE_IIFORMAT): Fix bug found by Andy. + (INITIALIZE_IMAGE_INSTANTIATOR_FORMAT): Fix stupid bug. + (REINITIALIZE_IMAGE_INSTANTIATOR_FORMAT): Remove, useless once the + stupid bug fixed. + + * glyphs.c (reinit_image_instantiator_format_create): Remove. + + * glyphs-x.c (reinit_image_instantiator_format_create_glyphs_x): + Remove. + + * glyphs-widget.c + (reinit_image_instantiator_format_create_glyphs_widget): Remove. + + * glyphs-msw.c + (reinit_image_instantiator_format_create_glyphs_mswindows): + Remove. + + * glyphs-eimage.c + (reinit_image_instantiator_format_create_glyphs_eimage): Remove. + + * frame.c (Fmake_frame): Don't reset the face cache when using the + stream device. + + * file-coding.c: Dumped the_codesys_prop_dynarr and added all + relevant descriptions. + + * events.c (reinit_vars_of_events): Extracted from vars_of_events. + + * eval.c: The subr is _not_ a lcrecord. + + * emacs.c (main_1): Call vars_of_specifier early before any + specifier creation (e.g in vars_of_glyphs, at least). Remove the + useless reinit_image_instantiator_format*. Add + reinit_vars_of_events and reinit_complex_vars_of_minibuf. Add + calls to lstream_type_create* and process_type_create*. + + * elhash.c: Dump Vall_weak_hash_tables correctly. + + * data.c: Dump Vall_weak_lists correctly. + + * console.c: Fix description. + + * console-stream.c (init_console_stream): Do initializations + correctly in the pdump case. + + * chartab.c: Fix description. Dump Vall_syntax_tables correctly. + (Fcopy_char_table): Link into Vall_syntax_tables. + + * alloc.c (pdump_wire_list): Added. + (Fgarbage_collect): Fix loop in stats couting missing the last + lrecord type. + (pdump_register_sub): Added XD_LO_LINK. + (pdump_dump_data): Ditto. Fixed XD_LO_RESET_NIL forgttting the + counter. + (pdump_reloc_one): Ditto. + (pdump_scan_by_alignement): Use last_lrecord_type_index_assigned + instead of 256. + (pdump_dump_wired): Added lists. + (pdump): Use last_lrecord_type_index_assigned instead of 256. + Dump last_lrecord_type_index_assigned value. Fix minor bugs. + +1999-10-07 Andy Piper + + * glyphs-msw.c (mswindows_finalize_image_instance): zero out + bitmap slices. + + * glyphs-x.c (x_finalize_image_instance): fix FMW problem. + +1999-10-06 Andy Piper + + * elhash.c (resize_hash_table): Correct reference to lrecord_header. + +1999-10-06 Damon Lipparelli + + * elhash.h: forward declare Lisp_Hash_Table. + +1999-10-06 Andy Piper + + * glyphs.c (Fset_image_instance_property): mark glyphs as dirty + after setting an image instance property. + +1999-10-05 Andy Piper + + * gutter.c (update_frame_gutters): output gutters if + windows_changed is set. This is the only way of catching changes + in selected window which obviously can affect the specifiers. + + * redisplay.c: new state flags, subwindows_state_changed and + subwindows_state_changed set. + (redisplay_window): use them. + (redisplay_device): ditto. + (redisplay_without_hooks): ditto. + (redisplay_frame): ditto. Reset subwindow cachels if + subwindows_changed is set. + (redisplay_window): call mark_glyph_cachels_as_clean after + redisplaying. + + * redisplay-x.c (x_output_x_pixmap): select correct + pixmap image for display depending on the currently selected + slice. + + * redisplay-output.c (compare_runes): check dirtiness when + checking RUNE_DGLYPH runes. + (compare_display_blocks): relax invalidation of display blocks + since we can now detect whether individual glyphs have changed or + not. + + * redisplay-msw.c (mswindows_output_dibitmap): select correct + bitmap image for display depending on the currently selected + slice. + + * glyphs.h (struct Lisp_Image_Instance): add a dirty flag. + (IMAGE_INSTANCE_DIRTYP): new macro. + (XIMAGE_INSTANCE_DIRTYP): ditto. + (MARK_IMAGE_INSTANCE_CHANGED): ditto. + (GLYPH_DIRTYP): ditto. + (XGLYPH_DIRTYP): ditto. + (MARK_GLYPH_CHANGED): ditto. + (GLYPH_CACHEL_DIRTYP): ditto. + (struct glyph_cachel): add a dirty flag. + + * glyphs.c (update_frame_subwindows): Don't update on + glyphs_changed. + (glyph_animated_timeout_mapper): new function. Map over the + instance cache lookinng for animated images to update. + (Fglyph_animated_timeout_handler): new function. Lisp callback for + handling animated image timeout events. + (disable_glyph_animated_timeout): new function. Add the animated + image timeout. + (disable_glyph_animated_timeout): new function. Remove the + animated image timeout. + (syms_of_glyphs): initialize Qglyph_animated_timeout_handler and + friends. + (vars_of_glyphs): initialize Vglyph_animated_ticker. + (image_instance_equal): add the currently displayed slice. + (image_instance_hash): ditto. + (allocate_glyph): initialize dirty flag. + (glyph_width): rename glyph -> glyph_or_image. + (glyph_height_internal): ditto. + (glyph_dirty_p): new function. Determine whether the image + instance in the domain and/or glyph is dirty. + (set_glyph_dirty_p): set the dirtiness. + (update_glyph_cachel_data): take dirtiness into account. Pass the + image instance we are interested in to glyph_width and friends. + (get_glyph_cachel_index): make non-static. Always call + update_glyph_cachel_data. + (mark_glyph_cachels_as_not_updated): meaningless formatting + change. + (mark_glyph_cachels_as_clean): new function. Clean dirtiness from + glyph cachels. + + * glyphs-x.h (struct x_image_instance_data): change + pixmap to a list of pixmaps. + (IMAGE_INSTANCE_X_PIXMAP_SLICE): new macro. + (IMAGE_INSTANCE_X_PIXMAP_SLICES): ditto. + (XIMAGE_INSTANCE_X_PIXMAP_SLICE): ditto. + (XIMAGE_INSTANCE_X_PIXMAP_SLICES): ditto. + + * glyphs-x.c (x_finalize_image_instance): make sure multi pixmap + images get deleted properly. + (init_image_instance_from_x_image): add slices paramater and use + it to initialize x_image_instance_data correctly. + (image_instance_add_x_image): new function. Add new pixmaps to our + set of instantiated pixmaps for an image. Used by animated images. + (x_init_image_instance_from_eimage): add a slices + parameter. Instantiate all images from the eimage. + (x_xpm_instantiate): update use of + init_image_instance_from_x_image. + (init_image_instance_from_xbm_inline): ditto. + (x_initialize_pixmap_image_instance): add slices paramater and use + it to allocate x_image_instance_data correctly. + + * glyphs-msw.h (struct mswindows_image_instance_data): change + bitmap to a list of bitmaps. + (IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE): new macro. + (IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES): ditto. + (XIMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE): ditto. + (XIMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES): ditto. + + * glyphs-msw.c (init_image_instance_from_dibitmap): add slices + paramater and use it to initialize mswindows_image_instance_data + correctly. + (image_instance_add_dibitmap): new function. Add new bitmaps to + our set of instantiated bitmaps for an image. Used by animated + images. + (mswindows_init_image_instance_from_eimage): add a slices + parameter. Instantiate all images from the eimage. + (mswindows_xpm_instantiate): update use of + init_image_instance_from_dibitmap. + (bmp_instantiate): ditto. + (init_image_instance_from_xbm_inline): ditto. + (mswindows_finalize_image_instance): make sure all the bitmap + slices get deleted. + (mswindows_initialize_dibitmap_image_instance): add slices + paramater and use it to allocate mswindows_image_instance_data + correctly. + + * glyphs-eimage.c (jpeg_instantiate): give extra paramter to + init_image_instance_from_eimage. + (png_instantiate): ditto. + (tiff_instantiate): ditto. + (gif_instantiate): allocate bitmaps for all gif slices not just + the first one. + + * device.h (struct device): add subwindows_state_changed flag. + (MARK_DEVICE_SUBWINDOWS_STATE_CHANGED): new macro. + (MARK_DEVICE_FRAMES_GLYPHS_CHANGED): ditto. + + * console.h (struct console_methods): add a slice parameter to + init_image_instance_from_eimage_method. + + * redisplay.c (create_string_text_block): Allow buffer to be nil + without crashing. + +1999-09-24 Andy Piper + + * glyphs-x.c: only include gui-x.h if we are building with + widgets. + + * gui-x.c (vars_of_gui_x): only set popup_up_p if we have popups. + +1999-09-28 Lee Kindness + + * objects-x.c (allocate_nearest_color): will return 0 (failure) + when the colormap is full and the color it has computed to be the + 'nearest' has been allocated read/write. + +1999-10-02 Olivier Galibert + + * search.c (reinit_vars_of_search): Reinit the search cache + correctly. + + * elhash.h: Make the description visible. Declare + resize_hash_table. + + * elhash.c (resize_hash_table): Extracted from enlarge_hash_table + to generalize the hash table reorganization. + (reorganize_hash_table): Added. + (enlarge_hash_table): Uses resize_has_table. + + * casetab.c (complex_vars_of_casetab): staticpro the mule mirror + tables. + + * alloc.c: Add correct management of blocks of structures. + Reorganize hash tables at reload since the hash values can change + with the pointers. + +1999-10-01 Olivier Galibert + + * lisp.h: Add pdump_wire declaration + + * elhash.c (vars_of_elhash): Wire Vall_weak_hash_tables. + * symbols.c (init_symbols_once_early): Wire Qnil and Qunbound. + + * alloc.c (pdump_wire): Added.. + (pdump_load): Support it. + (pdump): Support it + + * glyphs-msw.c + (reinit_image_instantiator_format_create_glyphs_mswindows): Fix + macro calls. + +1999-09-28 Olivier Galibert + + * symsinit.h: Added lots of prototypes. + + * symeval.h: Added defsymbol_nodump declaration. + + * symbols.c (find_symbol_value): Lame attempt at making the + startup go further. + (defsymbol_nodump): Added. + + * mule-charset.c: Collapsed global lisp objects arrays in one + dumpable structure. + + * lrecord.h: Added some flags. + + * lisp.h: Added dumped flag to dynarrs. Added dumpstruct + declaration. + + * glyphs.h (INITIALIZE_IMAGE_INSTANTIATOR_FORMAT_NO_SYM): Don't + staticpro dynamic variables. + + * glyphs.c (reinit_specifier_type_create_image): Added. + (image_instantiator_format_create): Dump image instantiator format + dynarr. + (reinit_image_instantiator_format_create): Added. + + * emacs.c (main_1): Added reinits calls. + + * dynarr.c: Protect dumped dynarrays from going berzek in free or + realloc. + + * specifier.h (INITIALIZE_SPECIFIER_TYPE): Don't staticpro dynamic + variables. + * specifier.c (specifier_type_create): Dump the specifier type + dynarr. + (reinit_specifier_type_create): Added. + * console.h (INITIALIZE_CONSOLE_TYPE): Don't staticpro dynamic + variables. + * console.c (console_type_create): Dump the console type dynarr. + (reinit_vars_of_console): Extracted from vars_of_console. + (reinit_complex_vars_of_console): Extracted from + complex_vars_of_console + * window.c (reinit_vars_of_window): Extracted from vars_of_window. + * toolbar.c (reinit_specifier_type_create_toolbar): Added. + * search.c (reinit_vars_of_search): Extracted from vars_of_search. + * objects.c (reinit_specifier_type_create_objects): Added. + (reinit_vars_of_objects): Extracted from vars_of_objects. + * lstream.c (reinit_vars_of_lstream): Extracted from + vars_of_lstream. + * lread.c (reinit_vars_of_lread): Extracted from vars_of_lread. + * gutter.c (reinit_specifier_type_create_gutter): Added. + * glyphs-x.c (reinit_image_instantiator_format_create_glyphs_x): + Added. + * glyphs-widget.c + (reinit_image_instantiator_format_create_glyphs_widget): Added + * glyphs-msw.c + (reinit_image_instantiator_format_create_glyphs_mswindows): Added. + * glyphs-eimage.c + (reinit_image_instantiator_format_create_glyphs_eimage): Added. + * event-stream.c (reinit_vars_of_event_stream): Extracted from + vars_of_event_stream + * eval.c (reinit_vars_of_eval): Extracted from vars_of_eval. + * device.c (reinit_vars_of_device): Extracted from vars_of_device. + * console-x.c (reinit_console_type_create_x): Added. + * console-tty.c (reinit_console_type_create_tty): Added + * console-stream.c (reinit_console_type_create_stream): Added. + (init_console_stream): If PDUMP, always reinitialise basic + devices. + * console-msw.c (reinit_console_type_create_mswindows): Added. + * buffer.c (reinit_vars_of_buffer): Extracted from + init_vars_of_buffer. + (reinit_complex_vars_of_buffer): Extracted from + complex_vars_of_buffer + + * alloc.c: Further with the portable dumping, the revenge. + (dumpstruct): Added. + (reinit_alloc_once_early): Extracted from init_alloc_once_early. + + * specifier.c (sizeof_specifier): Correct size computation. + (make_specifier_internal): Ditto. + +1999-09-27 Olivier Galibert + + * alloc.c: Further with the portable dumping. + +1999-09-27 Martin Buchholz + + * glyphs-x.c (update_widget_face): Remove bogus cast + + * data.c (sign_extent_lisp): + * data.c (check_int_range): + * data.c (Faref): + * data.c (Faset): + * data.c (number_char_or_marker_to_int): + * data.c (number_char_or_marker_to_double): + * data.c (Frem): + * data.c (Fmod): + * extents.c (print_extent_1): + * fns.c (print_bit_vector): + * fns.c (Flength): + * fns.c (Fsafe_length): + * fns.c (copy_list): + * fns.c (Fsubseq): + * fns.c (Felt): + * fns.c (Flast): + * fns.c (Fnbutlast): + * insdel.h: + * marker.c (print_marker): + * syntax.h: + * bytecode.c (bytecode_arithcompare): + * bytecode.c (bytecode_arithop): + * lisp.h: + * lisp.h (EXTERNAL_LIST_LOOP_DELETE_IF): + * lisp.h (TRUE_LIST_P): + * lisp.h (CHECK_TRUE_LIST): + * lisp.h (bit_vector_length): + * lisp.h (GCPRO4): Make consistent. + * lisp.h (NGCPRO4): Make consistent. + * lisp.h (NNGCPRO4): Make consistent. + * alloc.c (Fmake_list): + * alloc.c (Fmake_string): + Use proper 64-bit types, e.g. EMACS_INT or size_t instead of int. + This should make all arithmetic 64-bit clean. + + Use %ld with (long) casts in print statements of types with sizes + possibly larger than int. + + Following functions had mismatched prototypes!!: + do_marker_adjustment(), fixup_internal_substring(), scan_lists(), + char_quoted(), make_string_from_buffer(), + make_string_from_buffer_no_extents() + + The types of Bufpos, Bytind, Memind, Bytecount, Charcount, + Extcount are all now EMACS_INT. I hope to see the day when I can + create a buffer with more than INT_MAX characters, without having + XEmacs slow down to a crawl. I also hope to be able to create a + list with more than INT_MAX cons cells. + + * redisplay.c (decode_mode_spec): + The %p and %P specs in the mode line were not correct for buffers + larger than MAX_INT/100! The %p spec was off by .5% even for + small buffers! + +1999-09-27 Martin Buchholz + + * cmdloop.c (num_input_keys): + * print.c (debug_temp): + * emacs.c (Vinfo_directory): + Delete unused variables + + * console-x.h (x_interline_space): Mark as unimplemented. + * redisplay-x.c (x_interline_space): Mark as unimplemented. + + * event-Xt.c (pending_timeouts): + * linuxplay.c (linuxplay_sndbuf): + * profile.c (QS*): + * search.c (searchbufs): + * specifier.c (specifier_type_entry_dynarr): + * undo.c (pending_boundary): + * event-stream.c (the_low_level_timeout_blocktype): + * extents.c (gap_array_marker_freelist): + * extents.c (extent_list_marker_freelist): + * print.c (being_printed): + * print.c (alternate_do_pointer): + * alloc.c (first_string_chars_block): + * alloc.c (current_string_chars_block): + * emacs.c (initial_argv): + * emacs.c (initial_argc): + * eval.c (lisp_eval_depth): + * free-hook.c (pointer_table): + * free-hook.c (free_queue): + * free-hook.c (current_free): + * free-hook.c (strict_free_check): + * redisplay.c (formatted_string_emchar_dynarr): + * redisplay.c (formatted_string_display_line): + * redisplay.c (formatted_string_extent_dynarr): + * redisplay.c (formatted_string_extent_start_dynarr): + * redisplay.c (formatted_string_extent_end_dynarr): + * redisplay.c (updating_line_start_cache): + * redisplay.c (last_display_warning_tick): + * redisplay.c (display_warning_tick): + * redisplay.c (internal_cache): + * window.c (Vwindow_configuration_free_list): + Make static. + + * redisplay.c (Vinitial_window_system): Make CONST. + +1999-09-24 Martin Buchholz + + * redisplay-tty.c (term_get_fkeys_1): Minor aesthetic improvements. + + * doprnt.c (get_doprnt_args): Use int, not short, with va_arg. + +1999-09-24 Andy Piper + + * redisplay-output.c (output_display_line): only clear the borders + if we are not displaying the gutter. + +1999-09-24 Jan Vroonhof + + * frame-x.c (x_any_window_to_frame): Let Xt find the widget and + then use x_any_widget_or_parent_to_frame(). + (x_find_frame_for_window): remove special cases. + +1999-09-24 Andy Piper + + * scrollbar-x.c (x_window_is_scrollbar): deleted. + * scrollbar-x.h: ditto. + +1999-09-23 Martin Buchholz + + * alloc.c (this_marks_a_marked_record): Remove. + + * buffer.c (mark_buffer): + * buffer.c (nuke_all_buffer_slots): + * console.c (mark_console): + * console.c (nuke_all_console_slots): + * frame.c (mark_frame): + * frame.c (nuke_all_frame_slots): + Treat MARKED_SLOT() macros consistently. + + * device.h (error_check_device_type): + * faces.c (face_getprop): + * fileio.c (DRIVE_LETTER): + * filelock.c (lock_file_1): + * frame-x.c (x_create_widgets): + * frame.h (error_check_frame_type): + * keymap.c (print_keymap): + * keymap.c (Fkey_description): + * keymap.c (where_is_recursive_mapper): + * mule-charset.h (CHARSET_LEADING_BYTE): + * objects-msw.c (mswindows_color_instance_hash): + * objects.c (color_instance_equal): + * objects.h (struct color_specifier): + * objects.h (struct font_specifier): + * objects.h (struct face_boolean_specifier): + * opaque.h (get_opaque_ptr): + * opaque.h (set_opaque_ptr): + * process-unix.c (set_socket_nonblocking_maybe): + * specifier.h (SPECIFIER_TYPE_P): + * symbols.c (store_symval_forwarding): + * syssignal.h (EMACS_KILLPG): + * terminfo.c (emacs_tparam): + * glyphs.c (glyph_putprop): + * glyphs.c (glyph_remprop): + * glyphs.c (Fimage_instance_subwindow_id): + * window.c (mark_window): + * window.c (mark_window_config): + * window.c (Fset_window_configuration): + * window.c (save_window_save): + * eval.c (Fuser_variable_p): + * eval.c (Fcommand_execute): + * eval.c (Feval): + * eval.c (Ffuncall): + * lisp.h (XPNTR): + * lisp.h (INT_OR_FLOATP): + * lisp.h (GC_INT_OR_FLOATP): + * lisp.h (XFLOATINT): + * lisp.h (IS_ANY_SEP): + * mule-ccl.c (Fccl_execute): + * mule-ccl.c (Fccl_execute_on_string): + * redisplay-x.c (x_output_string): + Remove redundant extra parentheses. + +1999-09-22 Martin Buchholz + + * chartab.c (word_boundary_p): Add prototype for warning avoidance. + * eval.c (PRIMITIVE_FUNCALL): ANSIfy + * free-hook.c (fun_ptr): ANSIfy + * getloadavg.c: Remove declaration for errno. + * gui.c (allocate_gui_item): ANSIfy + * gui.h (allocate_gui_item): ANSIfy + * mule-ccl.c (resolve_symbol_ccl_program): Make static + * realpath.c: Remove K&R support. + * redisplay-x.c (x_output_display_block): Don't shadow previous local + * glyphs-widget.c (layout_instantiate): Don't shadow previous local + * gutter.c (get_gutter_coords): Make static. + * lread.c (locate_file_map_suffixes): Make static. + * ralloc.c (relinquish): ANSIfy + * redisplay.c: + * lisp.h: + Move prototypes from redisplay.c to lisp.h + +1999-09-22 Martin Buchholz + + * glyphs-x.c (x_widget_set_property): + - Remove unnecessary initialization. + - Use char*, not Bufbyte *, with GET_C_STRING_OS_DATA_ALLOCA + * glyphs-x.c (x_widget_instantiate): + - Use char*, not Bufbyte *, with GET_C_STRING_OS_DATA_ALLOCA + * unexelf.c (unexec): + Add cast for C++ compilability. + * redisplay.h: + Fix a typo. + * ralloc.c (r_alloc_reinit): + SET_FUN_PTR was broken wrt ANSI aliasing! + To compensate, use __typeof__ when using gcc, else live with + possible (but rare) warnings. + * ralloc.c (init_ralloc): + Ditto + * ralloc.c: Use the real dlmalloc prototype for __morecore. + * lread.c (locate_file_map_suffixes): + * input-method-xlib.c (XIM_init_frame): + - Xlib functions should use XPointer, not XtPointer. + * input-method-xlib.c (XIM_delete_frame): + - Xlib functions should use XPointer, not XtPointer. + * input-method-xlib.c (IMDestroyCallback): + - Simplify. + - XFRAME (obj) can never be NULL, so don't test for it. + * gutter.h: + Add GUTTER_POS_LOOP for iterating over all gutter_pos'es + * gutter.c (SET_GUTTER_WAS_VISIBLE_FLAG): + Run c-backslash-region on macro body. + * gutter.c (gutter_was_visible): + Remove redundant parens - this is not a macro. + * gutter.c (redraw_exposed_gutters): + Use GUTTER_POS_LOOP. + * gutter.c (gutter_specs_changed): + Use GUTTER_POS_LOOP. + * gutter.c (gutter_geometry_changed_in_window): + Use GUTTER_POS_LOOP. + * gutter.c (update_frame_gutters): + Use GUTTER_POS_LOOP. + * gutter.c (init_frame_gutters): + Use GUTTER_POS_LOOP. + * file-coding.c (determine_real_coding_system): + Fix C++ compile error. + * emodules.c (find_make_module): + Cast return value from xrealloc + * emacs.c (Fkill_emacs): + Use __typeof__, when available. + * emacs.c (voodoo_free_hook): + Use __typeof__, when available. + (Unfortunately, the type of __free_hook is glibc-version-dependent) + * dired.c (user_cache): Use Bufbyte *, not char * + * dired.c (Fuser_name_all_completions): Ditto. + +1999-09-22 Andy Piper + + * redisplay.c (redisplay_frame): reset the gutter display lines + when we reset the subwindows. + + * gutter.c (reset_gutter_display_lines): new function. + + * window.c (Flast_nonminibuf_window): new function equivalent to + FRAME_LAST_NONMINIBUF_WINDOW (). + (syms_of_window): declare it. + + * redisplay.c (create_string_text_block): don't add bogus eol + markers to gutter display lines. + + * glyphs.c (reset_subwindow_cachels): make sure we unmap + subwindows using unmap_subwindow so that expose events get + registered correctly. + + * window.c (window_scroll): use Vwindow_pixel_scroll_increment to + determine how much to scroll the window. + (vars_of_window): Vwindow_pixel_scroll_increment is a new + variable. + +1999-09-20 Robert Pluim + + * glyphs-x.c (update_widget_face): Guard fontList declaration for + non-motif uses. + +1999-09-20 Andy Piper + + * glyphs-msw.c (mswindows_update_subwindow): update faces. + +1999-09-19 Andy Piper + + * glyphs.c (update_frame_subwindows): update if faces have + changed. + + * glyphs-x.c (x_widget_instantiate): create the clip widget using + lwlib rather than directly. + (x_finalize_image_instance): delete the clip widget using lwlib. + (x_update_subwindow): update widget faces. + (update_widget_face): new function for updating the face + properties of a widget. + (x_widget_set_property): update widget faces. + + * lwlib-Xlw.c (xlw_create_clip_window): new function. We need to + manage the clip widgets using lwlib so that we can delete them in + a safe manner. + +1999-09-16 Martin Buchholz + + * lisp-union.h: + * lisp-disunion.h: + Define new, potentially faster INT arithmetic macros + INT_PLUS, INT_MINUS, INT_PLUS1, INT_MINUS1 + * bytecode.c (execute_optimized_function): + Use new macros. + Fix metering code + * bytecode.c (bytecode_negate): + Optimize for integer case. + +1999-08-29 Andreas Jaeger + + * m/mips.h: Support for mips-linux: Add !linux around places + that are not valid for linux, define TEXT_START, DATA_START, + DATA_SEG_BITS. + +1999-09-16 Andy Piper + + * redisplay-output.c (redisplay_output_subwindow): clip subwindows + that don't completely fit on-screen rather than just unmapping + them. + + * glyphs.h: change signature of map_subwindow. + + * glyphs.c (map_subwindow): add display_glyph_area to the + signature. make sure the mapped area saved in the subwindow_cachel + reflects this. + (Fforce_subwindow_map): make a no-op. I don't think this does + anything useful. + + * glyphs-x.h (struct x_subwindow_data): save the Display rather + than the Screen. Add a clipwindow and clipwidget handle. + (IMAGE_INSTANCE_X_CLIPWINDOW): new accessor. + (IMAGE_INSTANCE_X_CLIPWIDGET): ditto. + (XIMAGE_INSTANCE_X_CLIPWIDGET): ditto. + (XIMAGE_INSTANCE_X_CLIPWINDOW): ditto. + + * glyphs-x.c (x_finalize_image_instance): destroy the clipwidget + as well as the widget itself. + (x_unmap_subwindow): unmap the clipwindow and clipwidget rather + than the widgets and subwindows themselves. move the widget inside + the clipwidget. + (x_subwindow_instantiate): hold onto the Display rather than the + Screen. allocate a clipwindow to put the subwindow inside. + (x_resize_subwindow): use saved Display directly. + (x_widget_instantiate): allocate a clipwidget of type EmacsManager + to put widgets inside. + + * glyphs-widget.c: remove group stuff. + + * glyphs-msw.h (struct mswindows_subwindow_data): new structure to + hold the clipwindow. + (IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW): new accessor. + (XIMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW): ditto. + + * glyphs-msw.c: remove group stuff. + (mswindows_finalize_image_instance): destroy clipwindow as well as + the widget itself. + (mswindows_unmap_subwindow): unmap the clipwindow rather than the + widget. + (mswindows_map_subwindow): ditto. move the widget within the + clipwindow. + (mswindows_subwindow_instantiate): allocate and initialize + mswindows_subwindow_data. allocate a clipwindow with the subwindow + as a child. + (mswindows_widget_instantiate): ditto. + (mswindows_control_wnd_proc): new function that allows us to + propagate events from the widget to the main windows control loop. + + * device-msw.c (mswindows_init_device): register new widget clip window + class. + + * console.h (struct console_methods): add display_glyph_area to + map_window. + + * console-msw.h: declare new window class and wnd proc for + widgets. + +1999-09-14 Martin Buchholz + + * general.c: + * eldap.c: + Move symbols used only by eldap.c into eldap.c as statics. + +1999-09-09 Martin Buchholz + + * window.c (syms_of_window): + * symbols.c (syms_of_symbols): + * redisplay.c (syms_of_redisplay): + * print.c (syms_of_print): + * lisp.h: + * intl.c (syms_of_intl): + * general.c (syms_of_general): + * frame.c (syms_of_frame): + * fileio.c (syms_of_fileio): + * file-coding.h: + * file-coding.c (syms_of_file_coding): + * extents.c (syms_of_extents): + * event-stream.c (syms_of_event_stream): + * event-stream.c (Fnext_event): + * device.c (syms_of_device): + * data.c (syms_of_data): + * casetab.c (syms_of_casetab): + * casetab.c (check_case_table): + * callint.c (syms_of_callint): + * buffer.c (syms_of_buffer): + Delete unused C symbols: + Qbuffer_file_name, Qbuffer_undo_list, Quser_variable_p, + Qcurrent_prefix_arg, Qtranslate_table, Qkeywordp, + Qnumber_or_marker_p, Qcons, Qkeyword, Qignore, Qdelete_device, + Qcommand_execute, Qglyph_invisible, + Qbuffer_file_coding_system, Qfile_name_handler_alist, + Qframe_x_p, Qframe_tty_p, Qblack, Qkeyboard, Qmenubar, Qpath, + Qvector, Qwhite, Qcase, Qdomain, Qalternate_debugging_output, + Qprint_escape_newlines, Qprint_readably, Qfloat_output_format, + Qwindow_scroll_functions, Qfboundp, Qscroll_up, Qscroll_down + + Rename symbols as required by the CHECK_RECORD macro: + - Qcase_table_p to Qcase_tablep + - Qcoding_system_p to Qcoding_systemp + + * debug.h: + * debug.c (syms_of_debug): + Make debug.c's internal Lisp_Objects static. + + * events.c (vars_of_events): + * events.c (syms_of_events): + Use regular old defsymbol instead of KEYSYM + staticpro(). + + * select-x.c (CHECK_CUTBUFFER): + Rewrite in accordance with coding standards. + + * keymap.c (syms_of_keymap): + Use SPC in the same way as RET, TAB, etc. + +1999-08-27 Jan Vroonhof + + * xemacs-20/src/menubar-x.c (make_dummy_xbutton_event): Don't add + offset twice if HAVE_WMCOMMAND is defined. + +1999-09-13 Mike McEwan + + * redisplay-x.c (x_output_vertical_divider): make sure + shadow_thickness is positive. + +1999-09-10 Julian Back + + * process-nt.c (nt_create_process): fixup to cope with + Vprocess_environment. + +1999-09-02 Andy Piper + + * redisplay-output.c (redisplay_output_layout): call output + routines with clear_clip false. output layout borders with text + correctly. + + * redisplay-msw.c (mswindows_output_blank): call output routines + with clear_clip true. + (mswindows_output_string): ditto. + (mswindows_output_display_block): ditto. + + * redisplay-x.c (x_output_display_block): call output routines + with clear_clip true. + + * redisplay.h: fix output routines for clear_clip parameter. + + * redisplay-output.c (redisplay_output_layout): cope with glyphs + in the border. + + * glyphs-widget.c (layout_instantiate): deal with border glyphs. + (check_valid_glyph_or_instantiator): renamed from + check_valid_glyph_or_image. + (check_valid_border): allow glyphs or their instantiators. + (check_valid_glyph_or_instantiator_list): renamed from + check_valid_glyph_or_image_list, + (glyph_instantiator_to_glyph): new function. make sure a glyph is + a glyph and not an instantiator. + (substitute_keyword_value): new function. replace a keyword value + with a new one. + +1999-09-01 Andy Piper + + * glyphs.c (string_set_property): new function to set the data of + a string. + (image_instantiator_format_create): use it. + +1999-09-07 Hrvoje Niksic + + * fns.c (Fmapc): Rename back to Fmapc_internal. + +1999-07-30 Gleb Arshinov + + * ntheap.h: CONST (semantically constant) name field of file_data + struct + + * unexnt.c (open_output_file): match function definition with + function declaration + + * editfns.c: #include "sysfile.h" for getcwd() prototype + + * gif_io.c: #include "sysfile.h" for close() prototype + +1999-09-02 Martin Buchholz + + * elhash.c: + * elhash.h: + Change the :type keyword to :weakness, for compatibility with the + GNU Emacs 20.5 hash table implementation. + Keep (but don't document) the :type keyword for compatibility. + Obsolete function hash-table-type + General cleanup. + Define function sxhash for compatibility with Common Lisp and GNU Emacs. + +1999-09-01 Martin Buchholz + + * floatfns.c (arith_error): + * floatfns.c (range_error): + * floatfns.c (range_error2): + * floatfns.c (domain_error): + * floatfns.c (domain_error2): + * lrecord.h (LRECORDP): + * console-x.h (X_ERROR_OCCURRED): + * console-x.h (HANDLING_X_ERROR): + * chartab.c (CATEGORYP): + * buffer.h (XCHAR_OR_CHAR_INT): + Remove redundant and confusing parentheses. + + * redisplay-output.c (redisplay_clear_to_window_end): + Remove redundant initialization. + + * redisplay.h: + * redisplay-msw.c: + * redisplay-x.c: + Move declarations of bevel_modeline() into redisplay.h. + +1999-08-30 Olivier Galibert + + * lisp.h: Add staticpro_nodump for undumped staticpro-ing. + * alloc.c: Add staticpro_nodump for undumped staticpro-ing. Add + alignment information for dumped data. Enhance + descriptions. Phase out Vterminal_* variables while + dumping. + * lrecord.h: Add chained descriptions and automagically-reset + lisp_objects to the description system. + + * console-stream.h: Declare the Vterminal_* variables. + + * buffer.c: Don't dump Vbuffer_alist, Vbuffer_defaults and + Vbuffer_local_symbols. + * console.c: Don't dump Vconsole_list, Vconsole_defaults and + Vconsole_local_symbols. + * eval.c: Don't dump Qunbound_suspended_errors_tag. + * lread.c: Don't dump Vread_buffer_stream. + * lstream.c: Don't dump Vlstream_free_list[]. + * search.c: Don't dump last_thing_searched. + * window.c: Don't dump minibuf_window and + Vwindow_configuration_free_list[]. + + * faces.c: Add face description. + * fns.c: Add bit_vector description. + * glyphs.c: Add image specifier description. + * objects.c: Add color, face and face boolean specifiers descriptions. + * opaque.c: Add opaque description. Don't dump Vopaque_ptr_free_list. + * rangetab.c: Add range table description. + * specifier.c: Add specifier and specifier methods description. + * specifier.h: Add specifier extra description support. + + * symbols.c: Fix symbol_value_buffer_local_description. + + * gdbinit (Lisp): Add opaque_ptr, remove opaque_list. + +1999-09-02 Hrvoje Niksic + + * extents.c (extent_remprop): Get extent's plist address + correctly. + +1999-08-31 Andy Piper + + * xmu.h: define Xmu/Converters.h things. + +1999-08-31 Andy Piper + + * opaque.c (equal_opaque_ptr): define. + (hash_opaque_ptr): define. + + * xmu.h: define Xmu/Misc.h things. + +1999-08-17 MORIOKA Tomohiko + + * file-coding.c (determine_real_coding_system): Treat `coding:' + cookie. + +1999-08-16 MORIOKA Tomohiko + + * file-coding.c (struct decoding_stream): New member `counter'. + (reset_decoding_stream): Initialize `counter'. + (decode_coding_ucs4): Use `counter'. + (decode_coding_utf8): Likewise. + +1999-08-31 Andy Piper + + * redisplay-output.c (redisplay_normalize_glyph_area): make sure + the clip offset doesn't exceed the height we have available to + show. + + * window.h (struct window): add top_yoffset and left_xoffset for + pixel scrolling. + (WINDOW_TEXT_TOP_CLIP): new macro. + + * window.c (window_scroll): add behaviour for pixel-scrolling of + tall lines. + + * redisplay.h (struct display_line): add top_clip. + (DISPLAY_LINE_HEIGHT): adjust for top_clip. + (DISPLAY_LINE_YPOS): ditto. + + * redisplay.c (position_redisplay_data_type): add + start_col_xoffset to prepare for pixel-based h-scrolling. + (WINDOW_SCROLLED): new macro. + (next_tab_position): use it. + (add_glyph_rune): use new hscoll vars. + (create_text_block): ditto. + (generate_displayable_area): adjust off-by-one error. + (regenerate_window): take top_clip into account. + (regenerate_window_extents_only_changed): ditto. + (regenerate_window_incrementally): ditto. + + * redisplay-x.c (x_output_display_block): use DISPLAY_LINE_YPOS, + DISPLAY_LINE_HEIGHT and DISPLAY_LINE_YEND macros. + (x_output_string): ditto. + (x_output_blank): ditto. + (x_output_hline): ditto. + (x_output_eol_cursor): ditto. + + * redisplay-output.c (output_display_line): allow for + top_clip. use DISPLAY_LINE_YPOS, DISPLAY_LINE_HEIGHT and + DISPLAY_LINE_YEND macros. + (redisplay_output_layout): output strings in layouts correctly. + (redisplay_clear_clipped_region): allow for top_clip. + (redisplay_calculate_display_boxes): ditto. + + * redisplay-msw.c (mswindows_output_blank): use DISPLAY_LINE_YPOS, + DISPLAY_LINE_HEIGHT and DISPLAY_LINE_YEND macros. + (mswindows_output_cursor): ditto. + (mswindows_output_string): ditto. + (mswindows_redraw_exposed_window): ditto. + (mswindows_output_display_block): ditto. + + * gutter.c: new specifier type gutter-size. + (gutter_size_validate): validate gutter-size specifier. + (Fgutter_size_specifier_p): predicate for gutter-size. + (Fredisplay_gutter_area): allow the gutter area to be redisplayed + under user contol, like Fredisplay_echo_area. + (syms_of_gutter): add new functions. + (specifier_type_create_gutter): add new specifier. + (specifier_vars_of_gutter): change specifier types of *-height to + gutter-size. + + * glyphs.c (glyph_width): make work with image instances. + + * console.h (struct console_methods): change api of output_string. + + * glyphs-x.c (x_map_subwindow): move before mapping as reported by + Stephen J. Turnbull + +1999-08-30 Andy Piper + + * glyphs-x.c (x_finalize_image_instance): X_MASK -> PIXMAP_MASK + for assignment. + (init_image_instance_from_x_image): ditto. + (x_xpm_instantiate): ditto. + (x_colorize_image_instance): ditto. Reported by Richard Cognot + + +1999-08-29 Andy Piper + + * glyphs-x.c (x_widget_instantiate): move font initialisation so + that it doesn't get saved in the user defined args. + (x_tab_control_instantiate): Set the fg color of the tab's + children. + (x_tab_control_set_property): ditto. + +1999-08-27 Damon Lipparelli + + * events.h (XTIMEOUT): must preface Lisp_Timeout with ``struct'' + (XSETTIMEOUT): fixup typo + +1999-08-11 Jan Vroonhof + + * syntax.c (scan_words): Unified Mule and Non-mule scanning. + Word boundary search looks back instead of forward so that it + doesn't peek over the limit. + +1999-08-20 Olivier Galibert + + * config.h.in: Add PDUMP define. + * emacs.c (Fdump_emacs): Hackish, call pdump() if configured in. + + * lrecord.h: Enhance description system. + * alloc.c: Fix vector and string description. Add portable + dumper enumeration fonctions. + + * symbols.c: Fix symbols description. Add symbol_value_forward + description. + * eval.c: Add subr description. + * elhash.c (CLEAR_HENTRY): Clean value pointer too. Fix hash + table description. + (remhash_1): CLEAR_HENTRY evaluates the parameter two times now. + +1999-08-20 Olivier Galibert + + * opaque.c: Kill opaque lists, make Lisp_Opaque_Ptr a lrecord of + its own. + * opaque.h: Ditto. + + * eval.c (eval_in_buffer_trapping_errors): + (run_hook_trapping_errors): + (safe_run_hook_trapping_errors): + (call0_trapping_errors): + (call1_trapping_errors): + (call2_trapping_errors): OPAQUEP -> OPAQUE_PTRP. make_opaque_ptr + now takes a non-const void *. + +1999-08-20 Olivier Galibert + + * opaque.c: Remove make_opaque_long. + + * opaque.h: Remove everything opaque_long related. + + * eval.c (vars_of_eval): Make Qunbound_suspended_errors_tag an + opaque_ptr. + + * emacs.c (main_1): Remove make_opaque_long from comment. + +1999-08-20 Olivier Galibert + + * event-stream.c (mark_timeout): + (print_timeout): + (event_stream_generate_wakeup): + (event_stream_resignal_wakeup): + (event_stream_disable_wakeup): + (event_stream_wakeup_pending_p): + (vars_of_event_stream): Lisp_Timeout is now a lrecord. + + * events.h (struct Lisp_Timeout): Added. + +1999-08-24 Andy Piper + + * console-x.h: declare new pixmap signatures. + +1999-08-23 Andy Piper + + * glyphs-x.c (x_update_subwindow): make sure the widget size is + maintained after an update. + + * event-Xt.c (emacs_Xt_handle_magic_event): use + find_matching_subwindow to check whether the exposure is totally + inside a subwindow, if it is then ignore it. + + * glyphs.c (find_matching_subwindow): new function. + + * toolbar-x.c (x_draw_blank_toolbar_button): use new + x_output_shadows signature. + (x_output_toolbar_button): use new x_output_x_pixmap signature. + + * redisplay.h (struct display_box): new structure. + (struct display_glyph_area): ditto. + declare new display_box functions. + + * redisplay-x.c (x_output_pixmap): update for new display + box stuff. + (x_bevel_area): update to allow multiple edge styles and border + segments. + (x_output_display_block): update for new display_box stuff and + signatures. + (x_clear_region): ditto. + (x_output_x_pixmap): ditto. adjust offsets rather than clip. + (console_type_create_redisplay_x): declare new console methods. + (x_output_vertical_divider): update for new bevel_area signature. + (x_output_shadows): update to allow selective drawing of edges. + + * redisplay-tty.c (tty_output_display_block): do nothing for + layouts. + + * redisplay-output.c (redisplay_output_subwindow): convert to use + display_box structure, this allows us to put subwindows anywhere + with any offset, useful for layout glyphs. + (redisplay_output_layout): new function. output a layout and its + sub-glyphs. + (redisplay_output_pixmap): new modular function combining generic + parts of the X and mswindows versions. convert to use display_box + structures. + (redisplay_clear_clipped_region): new function. clear the area a + glyph is going into. + (redisplay_normalize_glyph_area): new function. calculate the + bounds of a display_glyph_area given a display_box. + (redisplay_normalize_display_box): new function. shrink a + display_box to enclose a display_glyph_area. + (redisplay_display_boxes_in_window_p): check whether the input + display_box and display_glyph_area are actually in a window. + (redisplay_calculate_display_boxes): calculate display boxes based + on conventional display_line metrics. + (bevel_modeline): update for new bevel_area signature. + + * redisplay-msw.c (mswindows_output_blank): update for new + display_box stuff. + (mswindows_output_string): ditto. + (mswindows_output_dibitmap): ditto. + (mswindows_output_dibitmap_region): ditto. + (mswindows_output_pixmap): ditto. + (mswindows_bevel_area): update to allow multiple edge styles and + border segments. + (mswindows_output_display_block): update for new display_box stuff + and signatures. + (mswindows_clear_region): ditto. + (console_type_create_redisplay_mswindows): declare new console methods. + + * lisp.h (edge_style): new enum. + declare display_box and display_glyph_area. + + * gutter.c (output_gutter): update for new bevel_area signature. + + * glyphs.h (image_instance_type): add layout. + (IMAGE_LAYOUT_MASK): ditto. + (LAYOUT_IMAGE_INSTANCEP): new macro. + (CHECK_LAYOUT_IMAGE_INSTANCE): ditto. + (struct Lisp_Image_Instance): add offsets for layout and the + layout type itself. move mask here also. + (IMAGE_INSTANCE_LAYOUT_CHILDREN): new macro. + (IMAGE_INSTANCE_LAYOUT_BORDER): ditto. + (XIMAGE_INSTANCE_LAYOUT_CHILDREN): ditto. + (XIMAGE_INSTANCE_LAYOUT_BORDER): ditto. + + * glyphs.c (mark_image_instance): update for layouts. + (print_image_instance): ditto. + (image_instance_equal): ditto. + (image_instance_hash): ditto. + (allocate_image_instance): initialise offsets for layout. + (decode_image_instance_type): update for layouts. + (encode_image_instance_type): ditto. + (Fimage_instance_height): ditto. + (Fimage_instance_width): ditto. + (allocate_glyph): ditto. + (glyph_width): allow image instances as an argument. update for layouts. + (glyph_height_internal): ditto. + (syms_of_glyphs): add layout symbols. + + * glyphs-x.h (struct x_image_instance_data): remove mask entry. + (IMAGE_INSTANCE_X_MASK): update. + + * glyphs-x.c (x_label_instantiate): new function. instantiate a + label. + (image_instantiator_format_create_glyphs_x): initialise new layout + glyph type. + + * glyphs-widget.c: new layout type. + (check_valid_orientation): new keyword checker for layouts. + (check_valid_justification): ditto. + (check_valid_border): ditto. + (check_valid_glyph_or_image_list): ditto. + (layout_possible_dest_types): new function for layout glyph type. + (layout_normalize): ditto. + (layout_instantiate): ditto. + (syms_of_glyphs_widget): new keywords for layout. + (image_instantiator_format_create_glyphs_widget): initialise the + layout glyph type. + + * glyphs-msw.h (struct mswindows_image_instance_data): remove mask + argument. + (IMAGE_INSTANCE_MSWINDOWS_MASK): update. + + * glyphs-msw.c: declare layout format. + (image_instantiator_format_create_glyphs_mswindows): initialise it. + + * general.c: new symbols for layouts. + + * console.h (struct console_methods): new console methods for + outputting pixmaps and strings. + +1999-08-23 Didier Verna + + * sound.c: revert the renaming of `bell_volume' to `Vbell_volume' + and `bell_inhibit_time' to `Vbell_inhibit_time'. + +1999-08-18 Andy Piper + + * redisplay-output.c (redisplay_output_subwindow): disable + clipping attempt. + +1999-08-17 Andy Piper + + * gutter.c (redraw_exposed_gutter): handle degenerate case of no + area to expose or no gutter to display. + +1999-08-16 Charles G Waldman + + * sound.c: rename `bell_volume' to `Vbell_volume' and + `bell_inhibit_time' to `Vbell_inhibit_time'. + +1999-08-13 Charles G Waldman + + * sound.c: (bell-inhibit-time): New variable. + (ding): Use it. + (sound-alist): Fix docstring. + +1999-08-17 Andy Piper + + * gui-x.c (button_item_to_widget_value): xstrdup name so that + deleting it is ok. + +1999-08-16 Jeff Miller + + * syntax.c (scan_words): make compile. + +1999-08-16 Andy Piper + + * redisplay-output.c (redisplay_output_subwindow): try and be more + relaxed about clipping possibilities. + + * glyphs-x.c (x_tab_control_set_property): free_widget_value_tree + rather than just the widget_value. + (x_update_subwindow): ditto. + (x_widget_instantiate): ditto. + + * gutter.c (output_gutter): shrink current display lines if + required. + +1999-08-15 Andy Piper + + * redisplay.h: declare free_display_lines. + + * redisplay.c (free_display_lines): make non-static. + + * gutter.c (free_frame_gutters): use free_display_lines instead of + Dynarr_free. + (calculate_gutter_size): ditto. + +1999-08-12 Jan Vroonhof + + * eval.c (run_hook_with_args_in_buffer): GCPRO globals. + +1999-08-14 Andy Piper + + * glyphs.c (update_subwindow_cachel): make it less brittle. + +1999-08-04 Mike Woolley + + * scrollbar-msw.c (mswindows_handle_mousewheel_event): Fixed + problem in wheelmouse code occurring when the horizontal scrollbar + is enabled but not visible. + +1999-08-08 Andy Piper + + * toolbar-msw.c (mswindows_redraw_frame_toolbars): new function. + (console_type_create_toolbar_mswindows): use it. + + * glyphs.c (Fset_image_instance_property): fiddly reorganisation. + + * redisplay-output.c (redisplay_output_display_block): unmap + subwindows in the block area before outputting the block. + + * event-msw.c (mswindows_wnd_proc): check the update rect before + painting and disable expose registration while painting. + + * glyphs.c (register_ignored_expose): check + hold_ignored_expose_registration before registering expose events. + + * redisplay.c (redisplay_frame): reset the subwindow cache before + displaying the gutter. + + * glyphs-msw.c (mswindows_map_subwindow): move the window before + mapping. + + * gutter.c (update_frame_gutters): check for glyphs_changed as if + it is the subwindow cache will have been reset. + +1999-08-06 Andy Piper + + * gui-x.c (button_item_to_widget_value): cope with strings. + + * glyphs.h: declare global widget functions. + (IIFORMAT_HAS_SHARED_DEVMETHOD): new macro. + + * glyphs-x.c (x_combo_box_instantiate): do generic initialization + here. remove dead code. + (image_instantiator_format_create_glyphs_x): enable combo boxes + for Motif 2.0. + + * glyphs-widget.c (widget_instantiate_1): make non-static. + (tree_view_instantiate): renamed from combo_box_instantiate. + (image_instantiator_format_create_glyphs_widget): use new/changed methods. + + * glyphs-msw.c (mswindows_combo_box_instantiate): do generic + initialization here. + + * lwlib-Xm.c (xm_update_combo_box): new function. + (xm_update_one_widget): call it. + (xm_update_one_value): deal with combo boxes as well as lists. + (xm_create_combo_box): create a drop-down combo box. + + * toolbar-msw.c (mswindows_output_toolbar): call + mswindows_move_toolbar. + +1999-08-05 Andy Piper + + * window.c (Fcurrent_pixel_column): new function. use display + lines to calculate pixel position of point. + * window.c (syms_of_window): declare it. + +1999-08-05 Andy Piper + + * glyphs.c (check_for_ignored_expose): ignore exposures wholly + contained in our ignore list. + + * buffer.c (Frecord_buffer): add call to record-buffer-hook. + (syms_of_buffer): declare record-buffer-hook. + + * s/mingw32.h: define mousewheel things. + +1999-08-04 Mike Woolley + + * windowsnt.h (_WIN32_WINNT): enable for win95 + + * s/cygwin32.h: define mousewheel things. + + * scrollbar-msw.h: declare mousewheel handler. + + * scrollbar-msw.c (mswindows_handle_mousewheel_event): new function. + +1999-08-04 Andy Piper + + * gui-x.c (gui_items_to_widget_values): remove unused variable. + (gui_items_to_widget_values_1): ditto. + + * gui-x.h: unconditionally define since it is used everywhere. + +1999-08-04 Andy Piper + + * glyphs-x.c (x_finalize_image_instance): only free pixels if we + have that type of image. + +1999-07-30 Andy Piper + + * redisplay-output.c (redisplay_unmap_subwindows): add comparison + subwindow to not unmap if required. + (redisplay_unmap_subwindows_maybe): comparison is Qnil. + (redisplay_unmap_subwindows_except_us): new function. + (redisplay_output_subwindow): use it to unmap windows in the area + we are displaying into. + + * glyphs.c (update_subwindow_cachel_data): always update as we + only ever get called when an update is required. + (update_subwindow_cachel): new function. sync a subwindow with its + cachel. + (Fresize_subwindow): use it. + (register_ignored_expose): make sure we set the tail correctly. + +1999-07-28 Andy Piper + + * redisplay-output.c (redisplay_clear_bottom_of_window): remove + unneeded device. + + * gutter.c (redraw_exposed_gutter): unmap subwindows from the + whole gutter. + + * gui.h: declare parse_gui_item_tree_list and + parse_gui_item_tree_children. + + * gui.c (parse_gui_item_tree_item): new function for parsing item + lists into gui-item trees. + (parse_gui_item_tree_children): ditto. + (parse_gui_item_tree_list): ditto. + + * gui-x.h: declare gui_items_to_widget_values. + + * gui-x.c (gui_items_to_widget_values_1): new function for + recursively parsing gui-items into widget_values. + (gui_item_children_to_widget_values): ditto. + (gui_items_to_widget_values): ditto. + (sanity_check_lwlib): add widgets macrolets. + + * glyphs.h (IMAGE_INSTANCE_WIDGET_ITEMS): rename from *ITEM. + (XIMAGE_INSTANCE_WIDGET_ITEMS): ditto. + (IMAGE_INSTANCE_WIDGET_ITEM): rename from *SINGLE_ITEM. + (XIMAGE_INSTANCE_WIDGET_ITEM): ditto. + (struct expose_ignore): new structure for storing ignorable expose + events. + + * glyphs.c (valid_image_instantiator_format_p): fix so that using + a console-type as a locale works. + (mark_image_instance): ITEM->ITEMS. + (image_instance_equal): ditto. + (image_instance_hash): ditto. + (struct expose_ignore_blocktype): new blocktype. + (check_for_ignored_expose): new function. checks frame exposure + list for events to ignore. + (register_ignored_expose): new function. registers an expose event + as ignorable. + (unmap_subwindow): register the expose event as ignorable. + (vars_of_glyphs): initialise the exposure blocktype. + + * glyphs-x.c (x_finalize_image_instance): use lw_destroy_widget. + (x_update_subwindow): modify all widgets using widget_value tree + rather than just a single widget value. + (x_widget_instantiate): LWLIB_USES_MOTIF -> LWLIB_WIDGETS_MOTIF. + make sure widgets don't resize themselves. + (x_tab_control_instantiate): new function. use lwlib tab functions. + (x_tab_control_set_property): new function. + (image_instantiator_format_create_glyphs_x): add tab_control. + + * glyphs-widget.c (widget_text_to_pixel_conversion): calculate + slightly more sensibly. + (initialize_widget_image_instance): ITEM->ITEMS. + (widget_instantiate_1): parse gui items generically into the ITEMS + entry. + + * glyphs-msw.c (mswindows_update_subwindow): replace + SINGLE_ITEM->ITEM. + (mswindows_register_widget_instance): ditto. + (add_tree_item): modify to use new pre-initialised gui-item + structure. + (add_tab_item): ditto. + (mswindows_tab_control_instantiate): ditto. + (mswindows_tab_control_set_property): ditto. + (image_instantiator_format_create_glyphs_mswindows): predicate + existance of widgets on HAVE_WIDGETS. + + * frame.h (struct frame): add subwindow_exposures variables. + + * frame.c (allocate_frame_core): reset subwindow_exposures links. + + * event-msw.c (mswindows_wnd_proc): check for ignored + expose events before redrawing. + + * event-Xt.c (emacs_Xt_handle_magic_event): check for ignored + expose events before redrawing. + +1999-07-30 SL Baur + + * scrollbar-x.c: should include EmacsFrame.h. + From Jeff Miller + 1999-07-30 XEmacs Build Bot * XEmacs 21.2.19 is released 1999-07-27 Jeff Miller - * add a "#ifdef HAVE_MENUBARS" wrapper to gui.c around + * add a "#ifdef HAVE_MENUBARS" wrapper to gui.c around menubar_show_keybindings. 1999-07-23 SL Baur @@ -100,10 +1963,10 @@ * event-Xt.c (handle_focus_event_1): Re-enable Motif/XIM to get focus the event (XIM_focus_event). - (emacs_Xt_handle_magic_event): No side effect on Motif/XIM because + (emacs_Xt_handle_magic_event): No side effect on Motif/XIM because XIM_SetGeometry does nothing in input_method_motif.c, but re-unify the interface for future use (XIM_SetGeometry). - * redisplay-x.c (x_output_string): Re-enable Motif/XIM to set spot + * redisplay-x.c (x_output_string): Re-enable Motif/XIM to set spot location (XIM_SetSpotLocation). (x_output_eol_cursor): Ditto. @@ -211,7 +2074,7 @@ * redisplay-x.c (redisplay_clear_to_window_end): moved to redisplay.c - + * redisplay-msw.c (redisplay_clear_to_window_end): deleted. * gutter.c: new file - implements gutters. All new functions are @@ -350,9 +2213,9 @@ 1999-07-03 Gunnar Evermann - * tooltalk.c (init_tooltalk): save signal actions for SIGQUIT, - SIGINT and SIGCHLD before calling tt_open and restore the - afterwards. This fixes e.g. the zombie subprocesses on Solaris + * tooltalk.c (init_tooltalk): save signal actions for SIGQUIT, + SIGINT and SIGCHLD before calling tt_open and restore the + afterwards. This fixes e.g. the zombie subprocesses on Solaris 1999-07-06 SL Baur @@ -2277,8 +4140,8 @@ 1998-12-11 Martin Buchholz - * event-msw.c (mswindows_cancel_dispatch_event): - Gratuitous code prettification + * event-msw.c (mswindows_cancel_dispatch_event): + Gratuitous code prettification 1998-12-07 Hrvoje Niksic @@ -4103,7 +5966,7 @@ 1998-08-07 Matt Stupple - * ntproc.c: don't wait on char_consumed at thread entry. + * ntproc.c: don't wait on char_consumed at thread entry. Additionally, to get the 'process' marked as finished, ensure that the CHILD_ACTIVE macro returns false, so before exiting close char_avail and set it to NULL, and close other handles @@ -5396,7 +7259,7 @@ 1998-05-14 Damon Lipparelli - * winslots.h: close comment + * winslots.h: close comment 1998-05-16 Kirill M. Katsnelson diff -r 28d9c139be4c -r 11054d720c21 src/alloc.c --- a/src/alloc.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/alloc.c Mon Aug 13 11:26:11 2007 +0200 @@ -36,7 +36,7 @@ Added lcrecord lists for 19.14. slb: Lots of work on the purification and dump time code. Synched Doug Lea malloc support from Emacs 20.2. - og: Killed the purespace. + og: Killed the purespace. Portable dumper. */ #include @@ -57,11 +57,27 @@ #include "specifier.h" #include "sysfile.h" #include "window.h" +#include "console-stream.h" #ifdef DOUG_LEA_MALLOC #include #endif +#ifdef HAVE_MMAP +#include +#include +#endif + +#ifdef PDUMP +typedef struct +{ + const struct lrecord_description *desc; + int count; +} pdump_reloc_table; + +static char *pdump_rt_list = 0; +#endif + EXFUN (Fgarbage_collect, 0); /* Return the true size of a struct with a variable-length array field. */ @@ -183,13 +199,13 @@ int c_readonly (Lisp_Object obj) { - return POINTER_TYPE_P (XGCTYPE (obj)) && C_READONLY (obj); + return POINTER_TYPE_P (XTYPE (obj)) && C_READONLY (obj); } int lisp_readonly (Lisp_Object obj) { - return POINTER_TYPE_P (XGCTYPE (obj)) && LISP_READONLY (obj); + return POINTER_TYPE_P (XTYPE (obj)) && LISP_READONLY (obj); } @@ -359,8 +375,7 @@ void *val = xmalloc (len); if (val == 0) return 0; - memcpy (val, str, len); - return (char *) val; + return (char *) memcpy (val, str, len); } #ifdef NEED_STRDUP @@ -375,8 +390,7 @@ static void * allocate_lisp_storage (size_t size) { - void *p = xmalloc (size); - return p; + return xmalloc (size); } @@ -465,42 +479,17 @@ } } - -/* This must not be called -- it just serves as for EQ test - * If lheader->implementation->finalizer is this_marks_a_marked_record, - * then lrecord has been marked by the GC sweeper - * header->implementation is put back to its correct value by - * sweep_records */ -void -this_marks_a_marked_record (void *dummy0, int dummy1) -{ - abort (); -} - /* Semi-kludge -- lrecord_symbol_value_forward objects get stuck in CONST space and you get SEGV's if you attempt to mark them. This sits in lheader->implementation->marker. */ Lisp_Object -this_one_is_unmarkable (Lisp_Object obj, void (*markobj) (Lisp_Object)) +this_one_is_unmarkable (Lisp_Object obj) { abort (); return Qnil; } -/* XGCTYPE for records */ -int -gc_record_type_p (Lisp_Object frob, CONST struct lrecord_implementation *type) -{ - CONST struct lrecord_implementation *imp; - - if (XGCTYPE (frob) != Lisp_Type_Record) - return 0; - - imp = XRECORD_LHEADER_IMPLEMENTATION (frob); - return imp == type; -} - /************************************************************************/ /* Debugger support */ @@ -943,12 +932,12 @@ #define MINIMUM_ALLOWED_FIXED_TYPE_CELLS_cons 2000 static Lisp_Object -mark_cons (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_cons (Lisp_Object obj) { - if (GC_NILP (XCDR (obj))) + if (NILP (XCDR (obj))) return XCAR (obj); - markobj (XCAR (obj)); + mark_object (XCAR (obj)); return XCDR (obj); } @@ -1096,9 +1085,9 @@ { Lisp_Object val = Qnil; - int size = XINT (length); - - while (size-- > 0) + size_t size = XINT (length); + + while (size--) val = Fcons (init, val); return val; } @@ -1135,14 +1124,14 @@ /************************************************************************/ static Lisp_Object -mark_vector (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_vector (Lisp_Object obj) { Lisp_Vector *ptr = XVECTOR (obj); int len = vector_length (ptr); int i; for (i = 0; i < len - 1; i++) - markobj (ptr->contents[i]); + mark_object (ptr->contents[i]); return (len > 0) ? ptr->contents[len - 1] : Qnil; } @@ -1172,7 +1161,8 @@ static const struct lrecord_description vector_description[] = { { XD_LONG, offsetof(struct Lisp_Vector, size) }, - { XD_LISP_OBJECT, offsetof(struct Lisp_Vector, contents), XD_INDIRECT(0) } + { XD_LISP_OBJECT, offsetof(struct Lisp_Vector, contents), XD_INDIRECT(0, 0) }, + { XD_END } }; DEFINE_LRECORD_SEQUENCE_IMPLEMENTATION("vector", vector, @@ -1545,7 +1535,7 @@ f->constants = constants; CHECK_NATNUM (stack_depth); - f->stack_depth = XINT (stack_depth); + f->stack_depth = XINT (stack_depth); #ifdef COMPILED_FUNCTION_ANNOTATION_HACK if (!NILP (Vcurrent_compiled_function_annotation)) @@ -1557,7 +1547,7 @@ struct gcpro gcpro1; GCPRO1 (fun); /* don't let fun get reaped */ Vload_file_name_internal_the_purecopy = - Fpurecopy (Ffile_name_nondirectory (Vload_file_name_internal)); + Ffile_name_nondirectory (Vload_file_name_internal); f->annotated = Vload_file_name_internal_the_purecopy; UNGCPRO; } @@ -1736,11 +1726,11 @@ #define MINIMUM_ALLOWED_FIXED_TYPE_CELLS_string 1000 static Lisp_Object -mark_string (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_string (Lisp_Object obj) { struct Lisp_String *ptr = XSTRING (obj); - if (GC_CONSP (ptr->plist) && GC_EXTENT_INFOP (XCAR (ptr->plist))) + if (CONSP (ptr->plist) && EXTENT_INFOP (XCAR (ptr->plist))) flush_cached_extent_info (XCAR (ptr->plist)); return ptr->plist; } @@ -1754,8 +1744,9 @@ } static const struct lrecord_description string_description[] = { - { XD_STRING_DATA, offsetof(Lisp_String, data) }, - { XD_LISP_OBJECT, offsetof(Lisp_String, plist), 1 }, + { XD_BYTECOUNT, offsetof(Lisp_String, size) }, + { XD_OPAQUE_DATA_PTR, offsetof(Lisp_String, data), XD_INDIRECT(0, 1) }, + { XD_LISP_OBJECT, offsetof(Lisp_String, plist), 1 }, { XD_END } }; @@ -1791,8 +1782,8 @@ unsigned char string_chars[STRING_CHARS_BLOCK_SIZE]; }; -struct string_chars_block *first_string_chars_block; -struct string_chars_block *current_string_chars_block; +static struct string_chars_block *first_string_chars_block; +static struct string_chars_block *current_string_chars_block; /* If SIZE is the length of a string, this returns how many bytes * the string occupies in string_chars_block->string_chars @@ -2079,7 +2070,7 @@ memset (XSTRING_DATA (val), XCHAR (init), XSTRING_LENGTH (val)); else { - int i; + size_t i; Bufbyte *ptr = XSTRING_DATA (val); for (i = XINT (length); i; i--) @@ -2202,7 +2193,7 @@ It works like this: 1) Create an lcrecord-list object using make_lcrecord_list(). - This is often done at initialization. Remember to staticpro + This is often done at initialization. Remember to staticpro_nodump this object! The arguments to make_lcrecord_list() are the same as would be passed to alloc_lcrecord(). 2) Instead of calling alloc_lcrecord(), call allocate_managed_lcrecord() @@ -2223,7 +2214,7 @@ */ static Lisp_Object -mark_lcrecord_list (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_lcrecord_list (Lisp_Object obj) { struct lcrecord_list *list = XLCRECORD_LIST (obj); Lisp_Object chain = list->free; @@ -2376,6 +2367,7 @@ /* 415 used Mly 29-Jun-93 */ /* 1327 used slb 28-Feb-98 */ +/* 1328 used og 03-Oct-99 (moving slowly, heh?) */ #ifdef HAVE_SHLIB #define NSTATICS 4000 #else @@ -2399,24 +2391,89 @@ staticvec[staticidx++] = varaddress; } +/* Not "static" because of linker lossage on some systems */ +Lisp_Object *staticvec_nodump[200] + /* Force it into data space! */ + = {0}; +static int staticidx_nodump; + +/* Put an entry in staticvec_nodump, pointing at the variable whose address is given + */ +void +staticpro_nodump (Lisp_Object *varaddress) +{ + if (staticidx_nodump >= countof (staticvec_nodump)) + /* #### This is now a dubious abort() since this routine may be called */ + /* by Lisp attempting to load a DLL. */ + abort (); + staticvec_nodump[staticidx_nodump++] = varaddress; +} + +/* Not "static" because of linker lossage on some systems */ +struct { + void *data; + const struct struct_description *desc; +} dumpstructvec[200]; + +static int dumpstructidx; + +/* Put an entry in dumpstructvec, pointing at the variable whose address is given + */ +void +dumpstruct (void *varaddress, const struct struct_description *desc) +{ + if (dumpstructidx >= countof (dumpstructvec)) + abort (); + dumpstructvec[dumpstructidx].data = varaddress; + dumpstructvec[dumpstructidx].desc = desc; + dumpstructidx++; +} + +Lisp_Object *pdump_wirevec[50]; +static int pdump_wireidx; + +/* Put an entry in pdump_wirevec, pointing at the variable whose address is given + */ +void +pdump_wire (Lisp_Object *varaddress) +{ + if (pdump_wireidx >= countof (pdump_wirevec)) + abort (); + pdump_wirevec[pdump_wireidx++] = varaddress; +} + + +Lisp_Object *pdump_wirevec_list[50]; +static int pdump_wireidx_list; + +/* Put an entry in pdump_wirevec_list, pointing at the variable whose address is given + */ +void +pdump_wire_list (Lisp_Object *varaddress) +{ + if (pdump_wireidx_list >= countof (pdump_wirevec_list)) + abort (); + pdump_wirevec_list[pdump_wireidx_list++] = varaddress; +} + /* Mark reference to a Lisp_Object. If the object referred to has not been seen yet, recursively mark all the references contained in it. */ -static void +void mark_object (Lisp_Object obj) { tail_recurse: #ifdef ERROR_CHECK_GC - assert (! (GC_EQ (obj, Qnull_pointer))); + assert (! (EQ (obj, Qnull_pointer))); #endif /* Checks we used to perform */ /* if (EQ (obj, Qnull_pointer)) return; */ /* if (!POINTER_TYPE_P (XGCTYPE (obj))) return; */ /* if (PURIFIED (XPNTR (obj))) return; */ - if (XGCTYPE (obj) == Lisp_Type_Record) + if (XTYPE (obj) == Lisp_Type_Record) { struct lrecord_header *lheader = XRECORD_LHEADER (obj); #if defined (ERROR_CHECK_GC) @@ -2437,8 +2494,8 @@ #endif if (implementation->marker) { - obj = implementation->marker (obj, mark_object); - if (!GC_NILP (obj)) goto tail_recurse; + obj = implementation->marker (obj); + if (!NILP (obj)) goto tail_recurse; } } } @@ -2911,7 +2968,7 @@ /* Perhaps this will catch freeing an already-freed marker. */ Lisp_Object temmy; XSETMARKER (temmy, ptr); - assert (GC_MARKERP (temmy)); + assert (MARKERP (temmy)); #endif /* ERROR_CHECK_GC */ #ifndef ALLOC_NO_POOLS @@ -3124,18 +3181,18 @@ /* I hate duplicating all this crap! */ -static int +int marked_p (Lisp_Object obj) { #ifdef ERROR_CHECK_GC - assert (! (GC_EQ (obj, Qnull_pointer))); + assert (! (EQ (obj, Qnull_pointer))); #endif /* Checks we used to perform. */ /* if (EQ (obj, Qnull_pointer)) return 1; */ /* if (!POINTER_TYPE_P (XGCTYPE (obj))) return 1; */ /* if (PURIFIED (XPNTR (obj))) return 1; */ - if (XGCTYPE (obj) == Lisp_Type_Record) + if (XTYPE (obj) == Lisp_Type_Record) { struct lrecord_header *lheader = XRECORD_LHEADER (obj); #if defined (ERROR_CHECK_GC) @@ -3205,6 +3262,27 @@ sweep_events (); +#ifdef PDUMP + /* Unmark all dumped objects */ + { + int i; + char *p = pdump_rt_list; + if(p) + for(;;) + { + pdump_reloc_table *rt = (pdump_reloc_table *)p; + p += sizeof (pdump_reloc_table); + if (rt->desc) { + for (i=0; icount; i++) + { + UNMARK_RECORD_HEADER ((struct lrecord_header *)(*(EMACS_INT *)p)); + p += sizeof (EMACS_INT); + } + } else + break; + } + } +#endif } /* Clearing for disksave. */ @@ -3406,6 +3484,8 @@ int i; for (i = 0; i < staticidx; i++) mark_object (*(staticvec[i])); + for (i = 0; i < staticidx_nodump; i++) + mark_object (*(staticvec_nodump[i])); } { /* GCPRO() */ @@ -3450,8 +3530,8 @@ } } - mark_redisplay (mark_object); - mark_profiling_info (mark_object); + mark_redisplay (); + mark_profiling_info (); /* OK, now do the after-mark stuff. This is for things that are only marked when something else is marked (e.g. weak hash tables). @@ -3460,18 +3540,18 @@ weak hash table, the former one might get marked. So we have to iterate until nothing more gets marked. */ - while (finish_marking_weak_hash_tables (marked_p, mark_object) > 0 || - finish_marking_weak_lists (marked_p, mark_object) > 0) + while (finish_marking_weak_hash_tables () > 0 || + finish_marking_weak_lists () > 0) ; /* And prune (this needs to be called after everything else has been marked and before we do any sweeping). */ /* #### this is somewhat ad-hoc and should probably be an object method */ - prune_weak_hash_tables (marked_p); - prune_weak_lists (marked_p); - prune_specifiers (marked_p); - prune_syntax_tables (marked_p); + prune_weak_hash_tables (); + prune_weak_lists (); + prune_specifiers (); + prune_syntax_tables (); gc_sweep (); @@ -3565,7 +3645,7 @@ garbage_collect_1 (); - for (i = 0; i < last_lrecord_type_index_assigned; i++) + for (i = 0; i <= last_lrecord_type_index_assigned; i++) { if (lcrecord_stats[i].bytes_in_use != 0 || lcrecord_stats[i].bytes_freed != 0 @@ -3839,32 +3919,8 @@ /* Initialization */ void -init_alloc_once_early (void) +reinit_alloc_once_early (void) { - int iii; - - last_lrecord_type_index_assigned = -1; - for (iii = 0; iii < countof (lrecord_implementations_table); iii++) - { - lrecord_implementations_table[iii] = 0; - } - - /* - * All the staticly - * defined subr lrecords were initialized with lheader->type == 0. - * See subr_lheader_initializer in lisp.h. Force type index 0 to be - * assigned to lrecord_subr so that those predefined indexes match - * reality. - */ - lrecord_type_index (&lrecord_subr); - assert (*(lrecord_subr.lrecord_type_index) == 0); - /* - * The same is true for symbol_value_forward objects, except the - * type is 1. - */ - lrecord_type_index (&lrecord_symbol_value_forward); - assert (*(lrecord_symbol_value_forward.lrecord_type_index) == 1); - gc_generation_number[0] = 0; /* purify_flag 1 is correct even if CANNOT_DUMP. * loadup.el will set to nil at end. */ @@ -3894,7 +3950,11 @@ init_event_alloc (); ignore_malloc_warnings = 0; - staticidx = 0; + + staticidx_nodump = 0; + dumpstructidx = 0; + pdump_wireidx = 0; + consing_since_gc = 0; #if 1 gc_cons_threshold = 500000; /* XEmacs change */ @@ -3923,6 +3983,38 @@ #endif /* ERROR_CHECK_TYPECHECK */ } +void +init_alloc_once_early (void) +{ + int iii; + + reinit_alloc_once_early (); + + last_lrecord_type_index_assigned = -1; + for (iii = 0; iii < countof (lrecord_implementations_table); iii++) + { + lrecord_implementations_table[iii] = 0; + } + + /* + * All the staticly + * defined subr lrecords were initialized with lheader->type == 0. + * See subr_lheader_initializer in lisp.h. Force type index 0 to be + * assigned to lrecord_subr so that those predefined indexes match + * reality. + */ + lrecord_type_index (&lrecord_subr); + assert (*(lrecord_subr.lrecord_type_index) == 0); + /* + * The same is true for symbol_value_forward objects, except the + * type is 1. + */ + lrecord_type_index (&lrecord_symbol_value_forward); + assert (*(lrecord_symbol_value_forward.lrecord_type_index) == 1); + + staticidx = 0; +} + int pure_bytes_used = 0; void @@ -4030,8 +4122,7 @@ image instance) in the domain of the selected frame, the mouse pointer will change instead of this message being printed. */ ); - Vgc_message = make_string_nocopy ((CONST Bufbyte *) gc_default_message, - countof (gc_default_message) - 1); + Vgc_message = build_string (gc_default_message); DEFVAR_LISP ("gc-pointer-glyph", &Vgc_pointer_glyph /* Pointer glyph used to indicate that a garbage collection is in progress. @@ -4048,3 +4139,982 @@ { Vgc_pointer_glyph = Fmake_glyph_internal (Qpointer); } + + +#ifdef PDUMP + +/* The structure of the file + * + * 0 - header + * 256 - dumped objects + * stab_offset - nb_staticpro*(Lisp_Object *) from staticvec + * - nb_staticpro*(relocated Lisp_Object) pointed to by staticpro + * - nb_structdmp*pair(void *, adr) for pointers to structures + * - lrecord_implementations_table[] + * - relocation table + * - wired variable address/value couples with the count preceding the list + */ +typedef struct +{ + char signature[8]; + EMACS_UINT stab_offset; + EMACS_UINT reloc_address; + int nb_staticpro; + int nb_structdmp; + int last_type; +} dump_header; + +char *pdump_start, *pdump_end; + +static const unsigned char align_table[256] = +{ + 8, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 6, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 7, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 6, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, + 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0 +}; + +typedef struct pdump_entry_list_elmt +{ + struct pdump_entry_list_elmt *next; + const void *obj; + size_t size; + int count; + int is_lrecord; + EMACS_INT save_offset; +} pdump_entry_list_elmt; + +typedef struct +{ + pdump_entry_list_elmt *first; + int align; + int count; +} pdump_entry_list; + +typedef struct pdump_struct_list_elmt +{ + pdump_entry_list list; + const struct struct_description *sdesc; +} pdump_struct_list_elmt; + +typedef struct +{ + pdump_struct_list_elmt *list; + int count; + int size; +} pdump_struct_list; + +static pdump_entry_list pdump_object_table[256]; +static pdump_entry_list pdump_opaque_data_list; +static pdump_struct_list pdump_struct_table; +static pdump_entry_list_elmt *pdump_qnil; + +static int pdump_alert_undump_object[256]; + +static unsigned long cur_offset; +static size_t max_size; +static int pdump_fd; +static void *pdump_buf; + +#define PDUMP_HASHSIZE 200001 + +static pdump_entry_list_elmt **pdump_hash; + +/* Since most pointers are eight bytes aligned, the >>3 allows for a better hash */ +static int +pdump_make_hash (const void *obj) +{ + return ((unsigned long)(obj)>>3) % PDUMP_HASHSIZE; +} + +static pdump_entry_list_elmt * +pdump_get_entry (const void *obj) +{ + int pos = pdump_make_hash(obj); + pdump_entry_list_elmt *e; + while ((e = pdump_hash[pos]) != 0) + { + if (e->obj == obj) + return e; + + pos++; + if (pos == PDUMP_HASHSIZE) + pos = 0; + } + return 0; +} + +static void +pdump_add_entry (pdump_entry_list *list, const void *obj, size_t size, int count, int is_lrecord) +{ + pdump_entry_list_elmt *e; + int align; + int pos = pdump_make_hash (obj); + + while ((e = pdump_hash[pos]) != 0) + { + if (e->obj == obj) + return; + + pos++; + if (pos == PDUMP_HASHSIZE) + pos = 0; + } + + e = malloc (sizeof (pdump_entry_list_elmt)); + + e->next = list->first; + e->obj = obj; + e->size = size; + e->count = count; + e->is_lrecord = is_lrecord; + list->first = e; + + list->count += count; + pdump_hash[pos] = e; + + align = align_table[size & 255]; + if (align<2 && is_lrecord) + align = 2; + + if(align < list->align) + list->align = align; +} + +static pdump_entry_list * +pdump_get_entry_list(const struct struct_description *sdesc) +{ + int i; + for(i=0; iname, + backtrace[i].position, + backtrace[i].offset); + } + } +} + +static void pdump_register_object (Lisp_Object obj); +static void pdump_register_struct (const void *data, const struct struct_description *sdesc, int count); + +static EMACS_INT +pdump_get_indirect_count (EMACS_INT code, const struct lrecord_description *idesc, const void *idata) +{ + EMACS_INT count; + const void *irdata; + + int line = XD_INDIRECT_VAL (code); + int delta = XD_INDIRECT_DELTA (code); + + irdata = ((char *)idata) + idesc[line].offset; + switch (idesc[line].type) { + case XD_SIZE_T: + count = *(size_t *)irdata; + break; + case XD_INT: + count = *(int *)irdata; + break; + case XD_LONG: + count = *(long *)irdata; + break; + case XD_BYTECOUNT: + count = *(Bytecount *)irdata; + break; + default: + fprintf (stderr, "Unsupported count type : %d (line = %d, code=%ld)\n", idesc[line].type, line, (long)code); + pdump_backtrace (); + abort (); + } + count += delta; + return count; +} + +static void +pdump_register_sub (const void *data, const struct lrecord_description *desc, int me) +{ + int pos; + const void *rdata; + + restart: + for (pos = 0; desc[pos].type != XD_END; pos++) + { + backtrace[me].position = pos; + backtrace[me].offset = desc[pos].offset; + + rdata = ((const char *)data) + desc[pos].offset; + switch(desc[pos].type) + { + case XD_SPECIFIER_END: + pos = 0; + desc = ((const struct Lisp_Specifier *)data)->methods->extra_description; + goto restart; + case XD_SIZE_T: + case XD_INT: + case XD_LONG: + case XD_BYTECOUNT: + case XD_LO_RESET_NIL: + case XD_INT_RESET: + case XD_LO_LINK: + break; + case XD_OPAQUE_DATA_PTR: + { + EMACS_INT count = desc[pos].data1; + if (XD_IS_INDIRECT(count)) + count = pdump_get_indirect_count (count, desc, data); + + pdump_add_entry (&pdump_opaque_data_list, + *(void **)rdata, + count, + 1, + 0); + break; + } + case XD_C_STRING: + { + const char *str = *(const char **)rdata; + if (str) + pdump_add_entry (&pdump_opaque_data_list, str, strlen (str)+1, 1, 0); + break; + } + case XD_DOC_STRING: + { + const char *str = *(const char **)rdata; + if ((EMACS_INT)str > 0) + pdump_add_entry (&pdump_opaque_data_list, str, strlen (str)+1, 1, 0); + break; + } + case XD_LISP_OBJECT: + { + EMACS_INT count = desc[pos].data1; + int i; + if (XD_IS_INDIRECT (count)) + count = pdump_get_indirect_count (count, desc, data); + + for(i=0;idescription) + { + int me = depth++; + if (me>65536) + { + fprintf (stderr, "Backtrace overflow, loop ?\n"); + abort (); + } + backtrace[me].obj = obj; + backtrace[me].position = 0; + backtrace[me].offset = 0; + + pdump_add_entry (pdump_object_table + XRECORD_LHEADER (obj)->type, + XRECORD_LHEADER (obj), + XRECORD_LHEADER_IMPLEMENTATION (obj)->static_size ? + XRECORD_LHEADER_IMPLEMENTATION (obj)->static_size : + XRECORD_LHEADER_IMPLEMENTATION (obj)->size_in_bytes_method (XRECORD_LHEADER (obj)), + 1, + 1); + pdump_register_sub (XRECORD_LHEADER (obj), + XRECORD_LHEADER_IMPLEMENTATION (obj)->description, + me); + --depth; + } + else + { + pdump_alert_undump_object[XRECORD_LHEADER (obj)->type]++; + fprintf (stderr, "Undumpable object type : %s\n", XRECORD_LHEADER_IMPLEMENTATION (obj)->name); + pdump_backtrace (); + } +} + +static void +pdump_register_struct (const void *data, const struct struct_description *sdesc, int count) +{ + if (data && !pdump_get_entry (data)) + { + int me = depth++; + int i; + if (me>65536) + { + fprintf (stderr, "Backtrace overflow, loop ?\n"); + abort (); + } + backtrace[me].obj = 0; + backtrace[me].position = 0; + backtrace[me].offset = 0; + + pdump_add_entry (pdump_get_entry_list (sdesc), + data, + sdesc->size, + count, + 0); + for (i=0; isize*i, + sdesc->description, + me); + } + --depth; + } +} + +static void +pdump_dump_data (pdump_entry_list_elmt *elmt, const struct lrecord_description *desc) +{ + size_t size = elmt->size; + int count = elmt->count; + if (desc) + { + int pos, i; + void *rdata; + memcpy (pdump_buf, elmt->obj, size*count); + + for (i=0; iobj))->methods->extra_description; + goto restart; + case XD_SIZE_T: + case XD_INT: + case XD_LONG: + case XD_BYTECOUNT: + break; + case XD_LO_RESET_NIL: + { + EMACS_INT count = desc[pos].data1; + int i; + if (XD_IS_INDIRECT (count)) + count = pdump_get_indirect_count (count, desc, elmt->obj); + for (i=0; isave_offset; + break; + } + case XD_INT_RESET: + { + EMACS_INT val = desc[pos].data1; + if (XD_IS_INDIRECT (val)) + val = pdump_get_indirect_count (val, desc, elmt->obj); + *(int *)rdata = val; + break; + } + case XD_OPAQUE_DATA_PTR: + case XD_C_STRING: + case XD_STRUCT_PTR: + { + void *ptr = *(void **)rdata; + if (ptr) + *(EMACS_INT *)rdata = pdump_get_entry (ptr)->save_offset; + break; + } + case XD_LO_LINK: + { + Lisp_Object obj = *(Lisp_Object *)rdata; + pdump_entry_list_elmt *elmt1; + for(;;) + { + elmt1 = pdump_get_entry (XRECORD_LHEADER(obj)); + if (elmt1) + break; + obj = *(Lisp_Object *)(desc[pos].offset + (char *)(XRECORD_LHEADER (obj))); + } + *(EMACS_INT *)rdata = elmt1->save_offset; + break; + } + case XD_LISP_OBJECT: + { + EMACS_INT count = desc[pos].data1; + int i; + if (XD_IS_INDIRECT (count)) + count = pdump_get_indirect_count (count, desc, elmt->obj); + + for(i=0; isave_offset; + } + break; + } + case XD_DOC_STRING: + { + EMACS_INT str = *(EMACS_INT *)rdata; + if (str > 0) + *(EMACS_INT *)rdata = pdump_get_entry ((void *)str)->save_offset; + break; + } + default: + fprintf (stderr, "Unsupported dump type : %d\n", desc[pos].type); + abort (); + }; + } + } + } + write (pdump_fd, desc ? pdump_buf : elmt->obj, size*count); + if (elmt->is_lrecord && ((size*count) & 3)) + write (pdump_fd, "\0\0\0", 4-((size*count) & 3)); +} + +static void +pdump_reloc_one (void *data, EMACS_INT delta, const struct lrecord_description *desc) +{ + int pos; + void *rdata; + + restart: + for (pos = 0; desc[pos].type != XD_END; pos++) + { + rdata = ((char *)data) + desc[pos].offset; + switch (desc[pos].type) { + case XD_SPECIFIER_END: + pos = 0; + desc = ((const struct Lisp_Specifier *)data)->methods->extra_description; + goto restart; + case XD_SIZE_T: + case XD_INT: + case XD_LONG: + case XD_BYTECOUNT: + case XD_INT_RESET: + break; + case XD_OPAQUE_DATA_PTR: + case XD_C_STRING: + case XD_STRUCT_PTR: + case XD_LO_LINK: + { + EMACS_INT ptr = *(EMACS_INT *)rdata; + if (ptr) + *(EMACS_INT *)rdata = ptr+delta; + break; + } + case XD_LISP_OBJECT: + case XD_LO_RESET_NIL: + { + EMACS_INT count = desc[pos].data1; + int i; + if (XD_IS_INDIRECT (count)) + count = pdump_get_indirect_count (count, desc, data); + + for (i=0; i 0) + *(EMACS_INT *)rdata = str + delta; + break; + } + default: + fprintf (stderr, "Unsupported dump type : %d\n", desc[pos].type); + abort (); + }; + } +} + +static void +pdump_allocate_offset (pdump_entry_list_elmt *elmt, const struct lrecord_description *desc) +{ + size_t size = (elmt->is_lrecord ? (elmt->size + 3) & ~3 : elmt->size)*elmt->count; + elmt->save_offset = cur_offset; + if (size>max_size) + max_size = size; + cur_offset += size; +} + +static void +pdump_scan_by_alignement (void (*f)(pdump_entry_list_elmt *, const struct lrecord_description *)) +{ + int align, i; + const struct lrecord_description *idesc; + pdump_entry_list_elmt *elmt; + for (align=8; align>=0; align--) + { + for (i=0; i<=last_lrecord_type_index_assigned; i++) + if (pdump_object_table[i].align == align) + { + elmt = pdump_object_table[i].first; + if (!elmt) + continue; + idesc = lrecord_implementations_table[i]->description; + while (elmt) + { + f (elmt, idesc); + elmt = elmt->next; + } + } + + for (i=0; idescription; + while (elmt) + { + f (elmt, idesc); + elmt = elmt->next; + } + } + + elmt = pdump_opaque_data_list.first; + while (elmt) + { + if (align_table[elmt->size & 255] == align) + f (elmt, 0); + elmt = elmt->next; + } + } +} + +static void +pdump_dump_staticvec (void) +{ + Lisp_Object *reloc = malloc (staticidx*sizeof (Lisp_Object)); + int i; + write (pdump_fd, staticvec, staticidx*sizeof (Lisp_Object *)); + + for(i=0; isave_offset; + else + reloc[i] = obj; + } + write (pdump_fd, reloc, staticidx*sizeof (Lisp_Object)); + free (reloc); +} + +static void +pdump_dump_structvec (void) +{ + int i; + for (i=0; isave_offset; + write (pdump_fd, &adr, sizeof (adr)); + } +} + +static void +pdump_dump_itable (void) +{ + write (pdump_fd, lrecord_implementations_table, sizeof (lrecord_implementations_table)); +} + +static void +pdump_dump_rtables (void) +{ + int i, j; + pdump_entry_list_elmt *elmt; + pdump_reloc_table rt; + + for (i=0; i<=last_lrecord_type_index_assigned; i++) + { + elmt = pdump_object_table[i].first; + if(!elmt) + continue; + rt.desc = lrecord_implementations_table[i]->description; + rt.count = pdump_object_table[i].count; + write (pdump_fd, &rt, sizeof (rt)); + while (elmt) + { + EMACS_INT rdata = pdump_get_entry (XRECORD_LHEADER (elmt->obj))->save_offset; + write (pdump_fd, &rdata, sizeof (rdata)); + elmt = elmt->next; + } + } + + rt.desc = 0; + rt.count = 0; + write (pdump_fd, &rt, sizeof (rt)); + + for (i=0; idescription; + rt.count = pdump_struct_table.list[i].list.count; + write (pdump_fd, &rt, sizeof (rt)); + while (elmt) + { + EMACS_INT rdata = pdump_get_entry (XRECORD_LHEADER (elmt->obj))->save_offset; + for (j=0; jcount; j++) { + write (pdump_fd, &rdata, sizeof (rdata)); + rdata += elmt->size; + } + elmt = elmt->next; + } + } + rt.desc = 0; + rt.count = 0; + write (pdump_fd, &rt, sizeof (rt)); +} + +static void +pdump_dump_wired (void) +{ + EMACS_INT count = pdump_wireidx + pdump_wireidx_list; + int i; + + write (pdump_fd, &count, sizeof (count)); + + for (i=0; isave_offset; + write (pdump_fd, &pdump_wirevec[i], sizeof (pdump_wirevec[i])); + write (pdump_fd, &obj, sizeof (obj)); + } + + for (i=0; idescription; + for (pos = 0; desc[pos].type != XD_LO_LINK; pos++) + if (desc[pos].type == XD_END) + abort (); + + obj = *(Lisp_Object *)(desc[pos].offset + (char *)(XRECORD_LHEADER (obj))); + } + res = elmt->save_offset; + + write (pdump_fd, &pdump_wirevec_list[i], sizeof (pdump_wirevec_list[i])); + write (pdump_fd, &res, sizeof (res)); + } +} + +void +pdump (void) +{ + int i; + Lisp_Object t_console, t_device, t_frame; + int none; + dump_header hd; + + /* These appear in a DEFVAR_LISP, which does a staticpro() */ + t_console = Vterminal_console; + t_frame = Vterminal_frame; + t_device = Vterminal_device; + + Vterminal_console = Qnil; + Vterminal_frame = Qnil; + Vterminal_device = Qnil; + + pdump_hash = malloc (PDUMP_HASHSIZE*sizeof (pdump_entry_list_elmt *)); + memset (pdump_hash, 0, PDUMP_HASHSIZE*sizeof (pdump_entry_list_elmt *)); + + for (i=0; i<=last_lrecord_type_index_assigned; i++) + { + pdump_object_table[i].first = 0; + pdump_object_table[i].align = 8; + pdump_object_table[i].count = 0; + pdump_alert_undump_object[i] = 0; + } + pdump_struct_table.count = 0; + pdump_struct_table.size = -1; + + pdump_opaque_data_list.first = 0; + pdump_opaque_data_list.align = 8; + pdump_opaque_data_list.count = 0; + depth = 0; + + for (i=0; iname, pdump_alert_undump_object[i]); + } + if (!none) + return; + + for (i=0; inb_staticpro; + last_lrecord_type_index_assigned = ((dump_header *)(pdump_start))->last_type; + delta = ((EMACS_INT)pdump_start) - ((dump_header *)pdump_start)->reloc_address; + p = pdump_start + ((dump_header *)pdump_start)->stab_offset; + + /* Put back the staticvec in place */ + memcpy (staticvec, p, staticidx*sizeof (Lisp_Object *)); + p += staticidx*sizeof (Lisp_Object *); + for (i=0; inb_structdmp; i++) + { + void **adr = *(void **)p; + p += sizeof (void *); + *adr = (void *)((*(EMACS_INT *)p) + delta); + p += sizeof (EMACS_INT); + } + + /* Put back the lrecord_implementations_table */ + memcpy (lrecord_implementations_table, p, sizeof (lrecord_implementations_table)); + p += sizeof (lrecord_implementations_table); + + /* Give back their numbers to the lrecord implementations */ + for (i=0; ilrecord_type_index) = i; + last_lrecord_type_index_assigned = i; + } + + /* Do the relocations */ + pdump_rt_list = p; + count = 2; + for(;;) + { + pdump_reloc_table *rt = (pdump_reloc_table *)p; + p += sizeof (pdump_reloc_table); + if (rt->desc) { + for (i=0; icount; i++) + { + EMACS_INT adr = delta + *(EMACS_INT *)p; + *(EMACS_INT *)p = adr; + pdump_reloc_one ((void *)adr, delta, rt->desc); + p += sizeof (EMACS_INT); + } + } else + if(!(--count)) + break; + } + + /* Put the pdump_wire variables in place */ + count = *(EMACS_INT *)p; + p += sizeof(EMACS_INT); + + for (i=0; idesc) + break; + if (rt->desc == hash_table_description) + { + for (i=0; icount; i++) + { + struct Lisp_Hash_Table *ht = XHASH_TABLE (*(EMACS_INT *)p); + reorganize_hash_table (ht); + p += sizeof (EMACS_INT); + } + break; + } else + p += sizeof (EMACS_INT)*rt->count; + } + return 1; +} + +#endif diff -r 28d9c139be4c -r 11054d720c21 src/buffer.c --- a/src/buffer.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/buffer.c Mon Aug 13 11:26:11 2007 +0200 @@ -96,6 +96,7 @@ Setting the default value also goes through the alist of buffers and stores into each buffer that does not say it has a local value. */ Lisp_Object Vbuffer_defaults; +static void *buffer_defaults_saved_slots; /* This structure marks which slots in a buffer have corresponding default values in Vbuffer_defaults. @@ -133,6 +134,7 @@ /* This structure holds the names of symbols whose values may be buffer-local. It is indexed and accessed in the same way as the above. */ static Lisp_Object Vbuffer_local_symbols; +static void *buffer_local_symbols_saved_slots; /* Alist of all buffer names vs the buffers. */ /* This used to be a variable, but is no longer, @@ -189,7 +191,7 @@ Lisp_Object Qdefault_directory; Lisp_Object Qkill_buffer_hook; -Lisp_Object Qbuffer_file_name, Qbuffer_undo_list; +Lisp_Object Qrecord_buffer_hook; Lisp_Object Qrename_auto_save_file; @@ -220,7 +222,7 @@ } static Lisp_Object -mark_buffer (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_buffer (Lisp_Object obj) { struct buffer *buf = XBUFFER (obj); @@ -229,13 +231,13 @@ undo_threshold, undo_high_threshold); -#define MARKED_SLOT(x) ((void) (markobj (buf->x))); +#define MARKED_SLOT(x) mark_object (buf->x) #include "bufslots.h" #undef MARKED_SLOT - markobj (buf->extent_info); + mark_object (buf->extent_info); if (buf->text) - markobj (buf->text->line_number_cache); + mark_object (buf->text->line_number_cache); /* Don't mark normally through the children slot. (Actually, in this case, it doesn't matter.) */ @@ -1406,6 +1408,9 @@ XCDR (prev) = XCDR (XCDR (prev)); XCDR (lynk) = f->buffer_alist; f->buffer_alist = lynk; + + va_run_hook_with_args (Qrecord_buffer_hook, 1, buffer); + return Qnil; } @@ -1806,6 +1811,7 @@ defsymbol (&Qmode_class, "mode-class"); defsymbol (&Qrename_auto_save_file, "rename-auto-save-file"); defsymbol (&Qkill_buffer_hook, "kill-buffer-hook"); + defsymbol (&Qrecord_buffer_hook, "record-buffer-hook"); defsymbol (&Qpermanent_local, "permanent-local"); defsymbol (&Qfirst_change_hook, "first-change-hook"); @@ -1816,8 +1822,6 @@ defsymbol (&Qbefore_change_function, "before-change-function"); defsymbol (&Qafter_change_function, "after-change-function"); - defsymbol (&Qbuffer_file_name, "buffer-file-name"); - defsymbol (&Qbuffer_undo_list, "buffer-undo-list"); defsymbol (&Qdefault_directory, "default-directory"); defsymbol (&Qget_file_buffer, "get-file-buffer"); @@ -1870,20 +1874,26 @@ "Attempt to modify a protected field", Qerror); } +void +reinit_vars_of_buffer (void) +{ + staticpro_nodump (&Vbuffer_alist); + Vbuffer_alist = Qnil; + current_buffer = 0; +} + /* initialize the buffer routines */ void vars_of_buffer (void) { /* This function can GC */ + reinit_vars_of_buffer (); + staticpro (&QSFundamental); staticpro (&QSscratch); - staticpro (&Vbuffer_alist); - - QSFundamental = Fpurecopy (build_string ("Fundamental")); - QSscratch = Fpurecopy (build_string (DEFER_GETTEXT ("*scratch*"))); - - Vbuffer_alist = Qnil; - current_buffer = 0; + + QSFundamental = build_string ("Fundamental"); + QSscratch = build_string (DEFER_GETTEXT ("*scratch*")); DEFVAR_LISP ("change-major-mode-hook", &Vchange_major_mode_hook /* List of hooks to be run before killing local variables in a buffer. @@ -2063,21 +2073,21 @@ b->indirect_children = Qnil; b->own_text.line_number_cache = Qnil; -#define MARKED_SLOT(x) b->x = (zap); +#define MARKED_SLOT(x) b->x = zap #include "bufslots.h" #undef MARKED_SLOT } -void -complex_vars_of_buffer (void) +static void +common_init_complex_vars_of_buffer (void) { /* Make sure all markable slots in buffer_defaults are initialized reasonably, so mark_buffer won't choke. */ struct buffer *defs = alloc_lcrecord_type (struct buffer, &lrecord_buffer); struct buffer *syms = alloc_lcrecord_type (struct buffer, &lrecord_buffer); - staticpro (&Vbuffer_defaults); - staticpro (&Vbuffer_local_symbols); + staticpro_nodump (&Vbuffer_defaults); + staticpro_nodump (&Vbuffer_local_symbols); XSETBUFFER (Vbuffer_defaults, defs); XSETBUFFER (Vbuffer_local_symbols, syms); @@ -2193,11 +2203,57 @@ buffer_local_flags.buffer_file_coding_system = make_int (1<<14); #endif - /* #### Warning: 1<<28 is the largest number currently allowable + /* #### Warning: 1<<31 is the largest number currently allowable due to the XINT() handling of this value. With some rearrangement you can get 3 more bits. */ } - +} + +#define BUFFER_SLOTS_SIZE (offsetof (struct buffer, BUFFER_SLOTS_LAST_NAME) - offsetof (struct buffer, BUFFER_SLOTS_FIRST_NAME) + sizeof (Lisp_Object)) +#define BUFFER_SLOTS_COUNT (BUFFER_SLOTS_SIZE / sizeof (Lisp_Object)) + +void +reinit_complex_vars_of_buffer (void) +{ + struct buffer *defs, *syms; + + common_init_complex_vars_of_buffer (); + + defs = XBUFFER (Vbuffer_defaults); + syms = XBUFFER (Vbuffer_local_symbols); + memcpy (&defs->BUFFER_SLOTS_FIRST_NAME, + buffer_defaults_saved_slots, + BUFFER_SLOTS_SIZE); + memcpy (&syms->BUFFER_SLOTS_FIRST_NAME, + buffer_local_symbols_saved_slots, + BUFFER_SLOTS_SIZE); +} + + +static const struct lrecord_description buffer_slots_description_1[] = { + { XD_LISP_OBJECT, 0, BUFFER_SLOTS_COUNT }, + { XD_END } +}; + +static const struct struct_description buffer_slots_description = { + BUFFER_SLOTS_SIZE, + buffer_slots_description_1 +}; + +void +complex_vars_of_buffer (void) +{ + struct buffer *defs, *syms; + + common_init_complex_vars_of_buffer (); + + defs = XBUFFER (Vbuffer_defaults); + syms = XBUFFER (Vbuffer_local_symbols); + buffer_defaults_saved_slots = &defs->BUFFER_SLOTS_FIRST_NAME; + buffer_local_symbols_saved_slots = &syms->BUFFER_SLOTS_FIRST_NAME; + dumpstruct (&buffer_defaults_saved_slots, &buffer_slots_description); + dumpstruct (&buffer_local_symbols_saved_slots, &buffer_slots_description); + DEFVAR_BUFFER_DEFAULTS ("default-modeline-format", modeline_format /* Default value of `modeline-format' for buffers that don't override it. This is the same as (default-value 'modeline-format). diff -r 28d9c139be4c -r 11054d720c21 src/buffer.h --- a/src/buffer.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/buffer.h Mon Aug 13 11:26:11 2007 +0200 @@ -219,7 +219,6 @@ #define XBUFFER(x) XRECORD (x, buffer, struct buffer) #define XSETBUFFER(x, p) XSETRECORD (x, p, buffer) #define BUFFERP(x) RECORDP (x, buffer) -#define GC_BUFFERP(x) GC_RECORDP (x, buffer) #define CHECK_BUFFER(x) CHECK_RECORD (x, buffer) #define CONCHECK_BUFFER(x) CONCHECK_RECORD (x, buffer) @@ -568,7 +567,7 @@ #else -#define XCHAR_OR_CHAR_INT(obj) (CHARP ((obj)) ? XCHAR ((obj)) : XINT ((obj))) +#define XCHAR_OR_CHAR_INT(obj) (CHARP (obj) ? XCHAR (obj) : XINT (obj)) #endif diff -r 28d9c139be4c -r 11054d720c21 src/bufslots.h --- a/src/bufslots.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/bufslots.h Mon Aug 13 11:26:11 2007 +0200 @@ -32,6 +32,10 @@ definition. In the garbage collector this file is included after defining MARKED_SLOT(x) to be mark_object(buffer->x). */ +#ifndef BUFFER_SLOTS_FIRST_NAME +#define BUFFER_SLOTS_FIRST_NAME name +#endif + /* The name of this buffer. */ MARKED_SLOT (name); @@ -235,6 +239,11 @@ /* A hash table that maps from a "generic extent" (an extent in `modeline-format') into a buffer-specific extent. */ MARKED_SLOT (modeline_extent_table); + +#ifndef BUFFER_SLOTS_LAST_NAME +#define BUFFER_SLOTS_LAST_NAME modeline_extent_table +#endif + #if 0 /* FSFmacs */ /* This is silly and stupid */ /* These are so we don't have to recompile everything diff -r 28d9c139be4c -r 11054d720c21 src/bytecode.c --- a/src/bytecode.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/bytecode.c Mon Aug 13 11:26:11 2007 +0200 @@ -235,21 +235,17 @@ Lisp_Object Vbyte_code_meter, Qbyte_code_meter; int byte_metering_on; -#define METER_2(code1, code2) \ - XINT (XVECTOR_DATA (XVECTOR_DATA (Vbyte_code_meter)[(code1)])[(code2)]) - -#define METER_1(code) METER_2 (0, (code)) - -#define METER_CODE(last_code, this_code) do { \ - if (byte_metering_on) \ - { \ - if (METER_1 (this_code) != ((1<specpdl_depth = XINT (Flength (f->arglist)) + varbind_count; f->instructions = - Fpurecopy (make_opaque (program_length * sizeof (Opbyte), - (CONST void *) program)); + make_opaque (program_length * sizeof (Opbyte), + (CONST void *) program); } assert (OPAQUEP (f->instructions)); @@ -1981,15 +1977,15 @@ static Lisp_Object -mark_compiled_function (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_compiled_function (Lisp_Object obj) { Lisp_Compiled_Function *f = XCOMPILED_FUNCTION (obj); - markobj (f->instructions); - markobj (f->arglist); - markobj (f->doc_and_interactive); + mark_object (f->instructions); + mark_object (f->arglist); + mark_object (f->doc_and_interactive); #ifdef COMPILED_FUNCTION_ANNOTATION_HACK - markobj (f->annotated); + mark_object (f->annotated); #endif /* tail-recurse on constants */ return f->constants; @@ -2350,10 +2346,8 @@ /* v18 or v19 bytecode file. Need to Ebolify. */ if (f->flags.ebolified && VECTORP (XCDR (tem))) ebolify_bytecode_constants (XCDR (tem)); - /* VERY IMPORTANT to purecopy here!!!!! - See load_force_doc_string_unwind. */ - f->instructions = Fpurecopy (XCAR (tem)); - f->constants = Fpurecopy (XCDR (tem)); + f->instructions = XCAR (tem); + f->constants = XCDR (tem); return function; } abort (); diff -r 28d9c139be4c -r 11054d720c21 src/bytecode.h --- a/src/bytecode.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/bytecode.h Mon Aug 13 11:26:11 2007 +0200 @@ -93,7 +93,6 @@ Lisp_Compiled_Function) #define XSETCOMPILED_FUNCTION(x, p) XSETRECORD (x, p, compiled_function) #define COMPILED_FUNCTIONP(x) RECORDP (x, compiled_function) -#define GC_COMPILED_FUNCTIONP(x) GC_RECORDP (x, compiled_function) #define CHECK_COMPILED_FUNCTION(x) CHECK_RECORD (x, compiled_function) #define CONCHECK_COMPILED_FUNCTION(x) CONCHECK_RECORD (x, compiled_function) diff -r 28d9c139be4c -r 11054d720c21 src/callint.c --- a/src/callint.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/callint.c Mon Aug 13 11:26:11 2007 +0200 @@ -58,9 +58,6 @@ Lisp_Object Qlet, QletX, Qsave_excursion; -Lisp_Object Qcurrent_prefix_arg; - -Lisp_Object Quser_variable_p; Lisp_Object Qread_from_minibuffer; Lisp_Object Qread_file_name; Lisp_Object Qread_directory_name; @@ -995,8 +992,6 @@ defsymbol (&Qevents_to_keys, "events-to-keys"); defsymbol (&Qcommand_debug_status, "command-debug-status"); defsymbol (&Qenable_recursive_minibuffers, "enable-recursive-minibuffers"); - defsymbol (&Quser_variable_p, "user-variable-p"); - defsymbol (&Qcurrent_prefix_arg, "current-prefix-arg"); defsymbol (&Qlet, "let"); defsymbol (&QletX, "let*"); diff -r 28d9c139be4c -r 11054d720c21 src/casetab.c --- a/src/casetab.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/casetab.c Mon Aug 13 11:26:11 2007 +0200 @@ -42,14 +42,13 @@ #include "buffer.h" #include "opaque.h" -Lisp_Object Qcase_table_p; +Lisp_Object Qcase_tablep; Lisp_Object Vascii_downcase_table, Vascii_upcase_table; Lisp_Object Vascii_canon_table, Vascii_eqv_table; #ifdef MULE Lisp_Object Vmirror_ascii_downcase_table, Vmirror_ascii_upcase_table; Lisp_Object Vmirror_ascii_canon_table, Vmirror_ascii_eqv_table; #endif -Lisp_Object Qtranslate_table; static void compute_trt_inverse (Lisp_Object trt, Lisp_Object inverse); @@ -81,7 +80,7 @@ REGISTER Lisp_Object tem; while (tem = Fcase_table_p (obj), NILP (tem)) - obj = wrong_type_argument (Qcase_table_p, obj); + obj = wrong_type_argument (Qcase_tablep, obj); return (obj); } @@ -289,8 +288,7 @@ void syms_of_casetab (void) { - defsymbol (&Qcase_table_p, "case-table-p"); - defsymbol (&Qtranslate_table, "translate-table"); + defsymbol (&Qcase_tablep, "case-table-p"); DEFSUBR (Fcase_table_p); DEFSUBR (Fcurrent_case_table); @@ -310,6 +308,13 @@ staticpro (&Vascii_canon_table); staticpro (&Vascii_eqv_table); +#ifdef MULE + staticpro (&Vmirror_ascii_downcase_table); + staticpro (&Vmirror_ascii_upcase_table); + staticpro (&Vmirror_ascii_canon_table); + staticpro (&Vmirror_ascii_eqv_table); +#endif + tem = MAKE_TRT_TABLE (); Vascii_downcase_table = tem; Vascii_canon_table = tem; diff -r 28d9c139be4c -r 11054d720c21 src/chartab.c --- a/src/chartab.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/chartab.c Mon Aug 13 11:26:11 2007 +0200 @@ -95,14 +95,14 @@ #ifdef MULE static Lisp_Object -mark_char_table_entry (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_char_table_entry (Lisp_Object obj) { struct Lisp_Char_Table_Entry *cte = XCHAR_TABLE_ENTRY (obj); int i; for (i = 0; i < 96; i++) { - markobj (cte->level2[i]); + mark_object (cte->level2[i]); } return Qnil; } @@ -143,16 +143,16 @@ #endif /* MULE */ static Lisp_Object -mark_char_table (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_char_table (Lisp_Object obj) { struct Lisp_Char_Table *ct = XCHAR_TABLE (obj); int i; for (i = 0; i < NUM_ASCII_CHARS; i++) - markobj (ct->ascii[i]); + mark_object (ct->ascii[i]); #ifdef MULE for (i = 0; i < NUM_LEADING_BYTES; i++) - markobj (ct->level1[i]); + mark_object (ct->level1[i]); #endif return ct->mirror_table; } @@ -162,18 +162,18 @@ and prune_weak_hash_tables(). */ void -prune_syntax_tables (int (*obj_marked_p) (Lisp_Object)) +prune_syntax_tables (void) { Lisp_Object rest, prev = Qnil; for (rest = Vall_syntax_tables; - !GC_NILP (rest); + !NILP (rest); rest = XCHAR_TABLE (rest)->next_table) { - if (! obj_marked_p (rest)) + if (! marked_p (rest)) { /* This table is garbage. Remove it from the list. */ - if (GC_NILP (prev)) + if (NILP (prev)) Vall_syntax_tables = XCHAR_TABLE (rest)->next_table; else XCHAR_TABLE (prev)->next_table = @@ -431,6 +431,8 @@ #ifdef MULE { XD_LISP_OBJECT, offsetof(struct Lisp_Char_Table, level1), NUM_LEADING_BYTES }, #endif + { XD_LISP_OBJECT, offsetof(struct Lisp_Char_Table, mirror_table), 1 }, + { XD_LO_LINK, offsetof(struct Lisp_Char_Table, next_table) }, { XD_END } }; @@ -707,7 +709,13 @@ ctnew->mirror_table = Fcopy_char_table (ct->mirror_table); else ctnew->mirror_table = ct->mirror_table; + ctnew->next_table = Qnil; XSETCHAR_TABLE (obj, ctnew); + if (ctnew->type == CHAR_TABLE_TYPE_SYNTAX) + { + ctnew->next_table = Vall_syntax_tables; + Vall_syntax_tables = obj; + } return obj; } @@ -1731,7 +1739,7 @@ #define CATEGORYP(x) \ - (CHARP ((x)) && XCHAR ((x)) >= 0x20 && XCHAR ((x)) <= 0x7E) + (CHARP (x) && XCHAR (x) >= 0x20 && XCHAR (x) <= 0x7E) #define CATEGORY_SET(c) \ (get_char_table(c, XCHAR_TABLE(current_buffer->category_table))) @@ -1746,6 +1754,7 @@ Use the macro WORD_BOUNDARY_P instead of calling this function directly. */ +int word_boundary_p (Emchar c1, Emchar c2); int word_boundary_p (Emchar c1, Emchar c2) { @@ -1839,6 +1848,7 @@ { /* DO NOT staticpro this. It works just like Vweak_hash_tables. */ Vall_syntax_tables = Qnil; + pdump_wire_list (&Vall_syntax_tables); } void diff -r 28d9c139be4c -r 11054d720c21 src/chartab.h --- a/src/chartab.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/chartab.h Mon Aug 13 11:26:11 2007 +0200 @@ -42,7 +42,6 @@ XRECORD (x, char_table_entry, struct Lisp_Char_Table_Entry) #define XSETCHAR_TABLE_ENTRY(x, p) XSETRECORD (x, p, char_table_entry) #define CHAR_TABLE_ENTRYP(x) RECORDP (x, char_table_entry) -#define GC_CHAR_TABLE_ENTRYP(x) GC_RECORDP (x, char_table_entry) /* #define CHECK_CHAR_TABLE_ENTRY(x) CHECK_RECORD (x, char_table_entry) char table entries should never escape to Lisp */ @@ -63,7 +62,6 @@ XRECORD (x, char_table, struct Lisp_Char_Table) #define XSETCHAR_TABLE(x, p) XSETRECORD (x, p, char_table) #define CHAR_TABLEP(x) RECORDP (x, char_table) -#define GC_CHAR_TABLEP(x) GC_RECORDP (x, char_table) #define CHECK_CHAR_TABLE(x) CHECK_RECORD (x, char_table) #define CONCHECK_CHAR_TABLE(x) CONCHECK_RECORD (x, char_table) @@ -186,7 +184,7 @@ int (*fn) (struct chartab_range *range, Lisp_Object val, void *arg), void *arg); -void prune_syntax_tables (int (*obj_marked_p) (Lisp_Object)); +void prune_syntax_tables (void); EXFUN (Fcopy_char_table, 1); EXFUN (Fmake_char_table, 1); diff -r 28d9c139be4c -r 11054d720c21 src/cmdloop.c --- a/src/cmdloop.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/cmdloop.c Mon Aug 13 11:26:11 2007 +0200 @@ -40,9 +40,6 @@ /* Current depth in recursive edits. */ int command_loop_level; -/* Total number of times command_loop has read a key sequence. */ -int num_input_keys; - #ifndef LISP_COMMAND_LOOP /* Form to evaluate (if non-nil) when Emacs is started. */ Lisp_Object Vtop_level; diff -r 28d9c139be4c -r 11054d720c21 src/config.h.in --- a/src/config.h.in Mon Aug 13 11:25:03 2007 +0200 +++ b/src/config.h.in Mon Aug 13 11:26:11 2007 +0200 @@ -272,6 +272,7 @@ #undef HAVE_GETTIMEOFDAY #undef HAVE_GETWD #undef HAVE_GETCWD +#undef HAVE_GETPT #undef HAVE_LOGB #undef HAVE_LRAND48 #undef HAVE_MATHERR @@ -294,6 +295,7 @@ #undef HAVE_SIGPROCMASK #undef HAVE_SIGSETJMP #undef HAVE_SNPRINTF +#undef HAVE_STPCPY #undef HAVE_STRCASECMP #undef HAVE_STRERROR #undef HAVE_TZSET @@ -597,12 +599,16 @@ #undef LWLIB_DIALOGS_MOTIF #undef LWLIB_DIALOGS_ATHENA #undef LWLIB_DIALOGS_ATHENA3D +#undef LWLIB_TABS_LUCID +#undef LWLIB_WIDGETS_MOTIF +#undef LWLIB_WIDGETS_ATHENA /* Other things that can be disabled by configure. */ #undef HAVE_MENUBARS #undef HAVE_SCROLLBARS #undef HAVE_DIALOGS #undef HAVE_TOOLBARS +#undef HAVE_WIDGETS #if defined (HAVE_MENUBARS) || defined (HAVE_DIALOGS) @@ -812,4 +818,6 @@ #undef INFODIR_USER_DEFINED #undef INFOPATH_USER_DEFINED +#undef PDUMP + #endif /* _SRC_CONFIG_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/conslots.h --- a/src/conslots.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/conslots.h Mon Aug 13 11:26:11 2007 +0200 @@ -25,6 +25,10 @@ definition. In the garbage collector this file is included after defining MARKED_SLOT(x) to be mark_object(console->x). */ +#ifndef CONSOLE_SLOTS_FIRST_NAME +#define CONSOLE_SLOTS_FIRST_NAME name +#endif + /* Name of this console, for resourcing and printing purposes. If not explicitly given, it's initialized in a console-specific manner. */ @@ -93,4 +97,7 @@ Initialized by the terminal-specific lisp files. */ MARKED_SLOT (function_key_map); +#ifndef CONSOLE_SLOTS_LAST_NAME +#define CONSOLE_SLOTS_LAST_NAME function_key_map +#endif diff -r 28d9c139be4c -r 11054d720c21 src/console-msw.c --- a/src/console-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -70,6 +70,12 @@ } void +reinit_console_type_create_mswindows (void) +{ + REINITIALIZE_CONSOLE_TYPE (mswindows); +} + +void vars_of_console_mswindows (void) { Fprovide (Qmswindows); diff -r 28d9c139be4c -r 11054d720c21 src/console-msw.h --- a/src/console-msw.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console-msw.h Mon Aug 13 11:26:11 2007 +0200 @@ -38,7 +38,7 @@ #endif #include #include /* DDE management library */ -#if !defined (__CYGWIN32__) && !defined(__MINGW32__) +#if !defined(__CYGWIN32__) && !defined(__MINGW32__) #include /* FileManager/Explorer drag and drop */ #include #endif @@ -66,6 +66,7 @@ /* The name of the main window class */ #define XEMACS_CLASS "XEmacs" +#define XEMACS_CONTROL_CLASS "XEmacsControl" /* * Console @@ -224,6 +225,9 @@ /* win32 "Windows" procedure */ LRESULT WINAPI mswindows_wnd_proc (HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam); +LRESULT WINAPI mswindows_control_wnd_proc (HWND hwnd, + UINT msg, WPARAM wParam, + LPARAM lParam); void mswindows_redraw_exposed_area (struct frame *f, int x, int y, int width, int height); diff -r 28d9c139be4c -r 11054d720c21 src/console-stream.c --- a/src/console-stream.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console-stream.c Mon Aug 13 11:26:11 2007 +0200 @@ -298,6 +298,12 @@ } void +reinit_console_type_create_stream (void) +{ + REINITIALIZE_CONSOLE_TYPE (stream); +} + +void vars_of_console_stream (void) { DEFVAR_LISP ("terminal-console", &Vterminal_console /* @@ -320,6 +326,7 @@ staticpro (&Vstdio_str); } +#ifndef PDUMP void init_console_stream (void) { @@ -339,3 +346,22 @@ event_stream_select_console (XCONSOLE (Vterminal_console)); } } + +#else + +void +init_console_stream (void) +{ + /* This function can GC */ + Vterminal_device = Fmake_device (Qstream, Qnil, Qnil); + Vterminal_console = Fdevice_console (Vterminal_device); + Vterminal_frame = Fmake_frame (Qnil, Vterminal_device); + minibuf_window = XFRAME (Vterminal_frame)->minibuffer_window; + if (initialized) + { + stream_init_console (XCONSOLE (Vterminal_console), Qnil); + if (noninteractive) + event_stream_select_console (XCONSOLE (Vterminal_console)); + } +} +#endif diff -r 28d9c139be4c -r 11054d720c21 src/console-stream.h --- a/src/console-stream.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console-stream.h Mon Aug 13 11:26:11 2007 +0200 @@ -40,6 +40,8 @@ #define CONSOLE_STREAM_DATA(con) CONSOLE_TYPE_DATA (con, stream) +extern Lisp_Object Vterminal_console, Vterminal_frame, Vterminal_device; + Lisp_Object stream_semi_canonicalize_console_connection(Lisp_Object, Error_behavior); Lisp_Object stream_canonicalize_console_connection(Lisp_Object, diff -r 28d9c139be4c -r 11054d720c21 src/console-tty.c --- a/src/console-tty.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console-tty.c Mon Aug 13 11:26:11 2007 +0200 @@ -166,12 +166,12 @@ } static void -tty_mark_console (struct console *con, void (*markobj) (Lisp_Object)) +tty_mark_console (struct console *con) { struct tty_console *tty_con = CONSOLE_TTY_DATA (con); - markobj (tty_con->terminal_type); - markobj (tty_con->instream); - markobj (tty_con->outstream); + mark_object (tty_con->terminal_type); + mark_object (tty_con->instream); + mark_object (tty_con->outstream); } static int @@ -372,6 +372,12 @@ } void +reinit_console_type_create_tty (void) +{ + REINITIALIZE_CONSOLE_TYPE (tty); +} + +void image_instantiator_format_create_glyphs_tty (void) { IIFORMAT_VALID_CONSOLE (tty, nothing); diff -r 28d9c139be4c -r 11054d720c21 src/console-x.c --- a/src/console-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -280,3 +280,9 @@ CONSOLE_HAS_METHOD (x, initially_selected_for_input); } + +void +reinit_console_type_create_x (void) +{ + REINITIALIZE_CONSOLE_TYPE (x); +} diff -r 28d9c139be4c -r 11054d720c21 src/console-x.h --- a/src/console-x.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console-x.h Mon Aug 13 11:26:11 2007 +0200 @@ -381,7 +381,7 @@ extern Lisp_Object Vdefault_x_device; /* Number of pixels below each line. */ -extern int x_interline_space; +extern int x_interline_space; /* #### implement me */ extern int x_selection_timeout; @@ -420,15 +420,14 @@ int cursor, int cursor_start, int cursor_width, int cursor_height); void x_output_x_pixmap (struct frame *f, struct Lisp_Image_Instance *p, - int x, int y, int clip_x, int clip_y, - int clip_width, int clip_height, int width, - int height, int pixmap_offset, + int x, int y, int xoffset, int yoffset, + int width, int height, unsigned long fg, unsigned long bg, GC override_gc); void x_output_shadows (struct frame *f, int x, int y, int width, int height, GC top_shadow_gc, GC bottom_shadow_gc, GC background_gc, - int shadow_thickness); + int shadow_thickness, int edges); void x_generate_shadow_pixels (struct frame *f, unsigned long *top_shadow, unsigned long *bottom_shadow, @@ -439,10 +438,10 @@ void x_init_modifier_mapping (struct device *d); #define X_ERROR_OCCURRED(dpy, body) \ - (expect_x_error ((dpy)), (body), x_error_occurred_p (dpy)) + (expect_x_error (dpy), body, x_error_occurred_p (dpy)) #define HANDLING_X_ERROR(dpy, body) \ - ( expect_x_error ((dpy)), (body), signal_if_x_error ((dpy), 0)) + (expect_x_error (dpy), body, signal_if_x_error (dpy, 0)) void Initialize_Locale (void); diff -r 28d9c139be4c -r 11054d720c21 src/console.c --- a/src/console.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console.c Mon Aug 13 11:26:11 2007 +0200 @@ -53,6 +53,7 @@ list of consoles and stores into each console that does not say it has a local value. */ Lisp_Object Vconsole_defaults; +static void *console_defaults_saved_slots; /* This structure marks which slots in a console have corresponding default values in console_defaults. @@ -69,7 +70,7 @@ consoles. If a slot is -1, then there is a DEFVAR_CONSOLE_LOCAL for it - as well as a default value which is used to initialize newly-created + as well as a default value which is used to initialize newly-created consoles and as a reset-value when local-vars are killed. If a slot is -2, there is no DEFVAR_CONSOLE_LOCAL for it. @@ -87,6 +88,7 @@ /* This structure holds the names of symbols whose values may be console-local. It is indexed and accessed in the same way as the above. */ static Lisp_Object Vconsole_local_symbols; +static void *console_local_symbols_saved_slots; DEFINE_CONSOLE_TYPE (dead); @@ -96,19 +98,19 @@ static Lisp_Object -mark_console (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_console (Lisp_Object obj) { struct console *con = XCONSOLE (obj); -#define MARKED_SLOT(x) ((void) (markobj (con->x))); +#define MARKED_SLOT(x) mark_object (con->x) #include "conslots.h" #undef MARKED_SLOT /* Can be zero for Vconsole_defaults, Vconsole_local_symbols */ if (con->conmeths) { - markobj (con->conmeths->symbol); - MAYBE_CONMETH (con, mark_console, (con, markobj)); + mark_object (con->conmeths->symbol); + MAYBE_CONMETH (con, mark_console, (con)); } return Qnil; @@ -1096,10 +1098,44 @@ defsymbol (&Qsuspend_resume_hook, "suspend-resume-hook"); } +static const struct lrecord_description cte_description_1[] = { + { XD_LISP_OBJECT, offsetof(console_type_entry, symbol), 1 }, + { XD_STRUCT_PTR, offsetof(console_type_entry, meths), 1, &console_methods_description }, + { XD_END } +}; + +static const struct struct_description cte_description = { + sizeof(console_type_entry), + cte_description_1 +}; + +static const struct lrecord_description cted_description_1[] = { + XD_DYNARR_DESC(console_type_entry_dynarr, &cte_description), + { XD_END } +}; + +const struct struct_description cted_description = { + sizeof(console_type_entry_dynarr), + cted_description_1 +}; + +static const struct lrecord_description console_methods_description_1[] = { + { XD_LISP_OBJECT, offsetof(struct console_methods, symbol), 2 }, + { XD_LISP_OBJECT, offsetof(struct console_methods, image_conversion_list), 1 }, + { XD_END } +}; + +const struct struct_description console_methods_description = { + sizeof(struct console_methods), + console_methods_description_1 +}; + + void console_type_create (void) { the_console_type_entry_dynarr = Dynarr_new (console_type_entry); + dumpstruct(&the_console_type_entry_dynarr, &cted_description); Vconsole_type_list = Qnil; staticpro (&Vconsole_type_list); @@ -1114,8 +1150,19 @@ } void +reinit_vars_of_console (void) +{ + staticpro_nodump (&Vconsole_list); + Vconsole_list = Qnil; + staticpro_nodump (&Vselected_console); + Vselected_console = Qnil; +} + +void vars_of_console (void) { + reinit_vars_of_console (); + DEFVAR_LISP ("create-console-hook", &Vcreate_console_hook /* Function or functions to call when a console is created. One argument, the newly-created console. @@ -1131,11 +1178,6 @@ */ ); Vdelete_console_hook = Qnil; - staticpro (&Vconsole_list); - Vconsole_list = Qnil; - staticpro (&Vselected_console); - Vselected_console = Qnil; - #ifdef HAVE_WINDOW_SYSTEM Fprovide (intern ("window-system")); #endif @@ -1184,13 +1226,13 @@ { zero_lcrecord (con); -#define MARKED_SLOT(x) con->x = (zap); +#define MARKED_SLOT(x) con->x = zap #include "conslots.h" #undef MARKED_SLOT } -void -complex_vars_of_console (void) +static void +common_init_complex_vars_of_console (void) { /* Make sure all markable slots in console_defaults are initialized reasonably, so mark_console won't choke. @@ -1198,8 +1240,8 @@ struct console *defs = alloc_lcrecord_type (struct console, &lrecord_console); struct console *syms = alloc_lcrecord_type (struct console, &lrecord_console); - staticpro (&Vconsole_defaults); - staticpro (&Vconsole_local_symbols); + staticpro_nodump (&Vconsole_defaults); + staticpro_nodump (&Vconsole_local_symbols); XSETCONSOLE (Vconsole_defaults, defs); XSETCONSOLE (Vconsole_local_symbols, syms); @@ -1254,6 +1296,53 @@ currently allowable due to the XINT() handling of this value. With some rearrangement you can get 4 more bits. */ } +} + + +#define CONSOLE_SLOTS_SIZE (offsetof (struct console, CONSOLE_SLOTS_LAST_NAME) - offsetof (struct console, CONSOLE_SLOTS_FIRST_NAME) + sizeof (Lisp_Object)) +#define CONSOLE_SLOTS_COUNT (CONSOLE_SLOTS_SIZE / sizeof (Lisp_Object)) + +void +reinit_complex_vars_of_console (void) +{ + struct console *defs, *syms; + + common_init_complex_vars_of_console (); + + defs = XCONSOLE (Vconsole_defaults); + syms = XCONSOLE (Vconsole_local_symbols); + memcpy (&defs->CONSOLE_SLOTS_FIRST_NAME, + console_defaults_saved_slots, + CONSOLE_SLOTS_SIZE); + memcpy (&syms->CONSOLE_SLOTS_FIRST_NAME, + console_local_symbols_saved_slots, + CONSOLE_SLOTS_SIZE); +} + + +static const struct lrecord_description console_slots_description_1[] = { + { XD_LISP_OBJECT, 0, CONSOLE_SLOTS_COUNT }, + { XD_END } +}; + +static const struct struct_description console_slots_description = { + CONSOLE_SLOTS_SIZE, + console_slots_description_1 +}; + +void +complex_vars_of_console (void) +{ + struct console *defs, *syms; + + common_init_complex_vars_of_console (); + + defs = XCONSOLE (Vconsole_defaults); + syms = XCONSOLE (Vconsole_local_symbols); + console_defaults_saved_slots = &defs->CONSOLE_SLOTS_FIRST_NAME; + console_local_symbols_saved_slots = &syms->CONSOLE_SLOTS_FIRST_NAME; + dumpstruct (&console_defaults_saved_slots, &console_slots_description); + dumpstruct (&console_local_symbols_saved_slots, &console_slots_description); DEFVAR_CONSOLE_DEFAULTS ("default-function-key-map", function_key_map /* Default value of `function-key-map' for consoles that don't override it. diff -r 28d9c139be4c -r 11054d720c21 src/console.h --- a/src/console.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/console.h Mon Aug 13 11:26:11 2007 +0200 @@ -60,6 +60,9 @@ DM_slow_device, DM_security }; +extern const struct struct_description cted_description; +extern const struct struct_description console_methods_description; + struct console_methods { CONST char *name; /* Used by print_console, print_device, print_frame */ @@ -68,7 +71,7 @@ /* console methods */ void (*init_console_method) (struct console *, Lisp_Object props); - void (*mark_console_method) (struct console *, void (*)(Lisp_Object)); + void (*mark_console_method) (struct console *); int (*initially_selected_for_input_method) (struct console *); void (*delete_console_method) (struct console *); Lisp_Object (*semi_canonicalize_console_connection_method) @@ -86,7 +89,7 @@ void (*init_device_method) (struct device *, Lisp_Object props); void (*finish_init_device_method) (struct device *, Lisp_Object props); void (*delete_device_method) (struct device *); - void (*mark_device_method) (struct device *, void (*)(Lisp_Object)); + void (*mark_device_method) (struct device *); void (*asynch_device_change_method) (void); Lisp_Object (*device_system_metrics_method) (struct device *, enum device_metrics); unsigned int (*device_implementation_flags_method) (void); @@ -103,7 +106,7 @@ void (*init_frame_3_method) (struct frame *); void (*after_init_frame_method) (struct frame *, int first_on_device, int first_on_console); - void (*mark_frame_method) (struct frame *, void (*)(Lisp_Object)); + void (*mark_frame_method) (struct frame *); void (*delete_frame_method) (struct frame *); void (*focus_on_frame_method) (struct frame *); void (*raise_frame_method) (struct frame *); @@ -155,15 +158,23 @@ int duration); void (*frame_redraw_cursor_method) (struct frame *f); void (*set_final_cursor_coords_method) (struct frame *, int, int); - void (*bevel_area_method) (struct window *, face_index, int, int, int, int, int); - + void (*bevel_area_method) (struct window *, face_index, int, int, int, int, int, + int, enum edge_style); + void (*output_pixmap_method) (struct window *w, Lisp_Object image_instance, + struct display_box *db, struct display_glyph_area *dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height, int offset_bitmap); + void (*output_string_method) (struct window *w, struct display_line *dl, + Emchar_dynarr *buf, int xpos, int xoffset, + int start_pixpos, int width, face_index findex, + int cursor, int cursor_start, int cursor_width, + int cursor_height); /* color methods */ int (*initialize_color_instance_method) (struct Lisp_Color_Instance *, Lisp_Object name, Lisp_Object device, Error_behavior errb); - void (*mark_color_instance_method) (struct Lisp_Color_Instance *, - void (*)(Lisp_Object)); + void (*mark_color_instance_method) (struct Lisp_Color_Instance *); void (*print_color_instance_method) (struct Lisp_Color_Instance *, Lisp_Object printcharfun, int escapeflag); @@ -182,8 +193,7 @@ Lisp_Object name, Lisp_Object device, Error_behavior errb); - void (*mark_font_instance_method) (struct Lisp_Font_Instance *, - void (*)(Lisp_Object)); + void (*mark_font_instance_method) (struct Lisp_Font_Instance *); void (*print_font_instance_method) (struct Lisp_Font_Instance *, Lisp_Object printcharfun, int escapeflag); @@ -204,14 +214,14 @@ Bytecount length); /* image methods */ - void (*mark_image_instance_method) (struct Lisp_Image_Instance *, - void (*)(Lisp_Object)); + void (*mark_image_instance_method) (struct Lisp_Image_Instance *); void (*print_image_instance_method) (struct Lisp_Image_Instance *, Lisp_Object printcharfun, int escapeflag); void (*finalize_image_instance_method) (struct Lisp_Image_Instance *); void (*unmap_subwindow_method) (struct Lisp_Image_Instance *); - void (*map_subwindow_method) (struct Lisp_Image_Instance *, int x, int y); + void (*map_subwindow_method) (struct Lisp_Image_Instance *, int x, int y, + struct display_glyph_area* dga); void (*resize_subwindow_method) (struct Lisp_Image_Instance *, int w, int h); void (*update_subwindow_method) (struct Lisp_Image_Instance *); int (*image_instance_equal_method) (struct Lisp_Image_Instance *, @@ -221,6 +231,7 @@ int depth); void (*init_image_instance_from_eimage_method) (struct Lisp_Image_Instance *ii, int width, int height, + int slices, unsigned char *eimage, int dest_mask, Lisp_Object instantiator, @@ -346,12 +357,19 @@ type##_console_methods = xnew_and_zero (struct console_methods); \ type##_console_methods->name = obj_name; \ type##_console_methods->symbol = Q##type; \ - defsymbol (&type##_console_methods->predicate_symbol, pred_sym); \ + defsymbol_nodump (&type##_console_methods->predicate_symbol, pred_sym); \ add_entry_to_console_type_list (Q##type, type##_console_methods); \ type##_console_methods->image_conversion_list = Qnil; \ - staticpro (&type##_console_methods->image_conversion_list); \ + staticpro_nodump (&type##_console_methods->image_conversion_list); \ + dumpstruct (&type##_console_methods, &console_methods_description); \ } while (0) +#define REINITIALIZE_CONSOLE_TYPE(type) do { \ + staticpro_nodump (&type##_console_methods->predicate_symbol); \ + staticpro_nodump (&type##_console_methods->image_conversion_list); \ +} while (0) + + /* Declare that console-type TYPE has method M; used in initialization routines */ #define CONSOLE_HAS_METHOD(type, m) \ @@ -402,7 +420,6 @@ #define XCONSOLE(x) XRECORD (x, console, struct console) #define XSETCONSOLE(x, p) XSETRECORD (x, p, console) #define CONSOLEP(x) RECORDP (x, console) -#define GC_CONSOLEP(x) GC_RECORDP (x, console) #define CHECK_CONSOLE(x) CHECK_RECORD (x, console) #define CONCHECK_CONSOLE(x) CONCHECK_RECORD (x, console) diff -r 28d9c139be4c -r 11054d720c21 src/data.c --- a/src/data.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/data.c Mon Aug 13 11:26:11 2007 +0200 @@ -50,14 +50,14 @@ Lisp_Object Qarith_error, Qrange_error, Qdomain_error; Lisp_Object Qsingularity_error, Qoverflow_error, Qunderflow_error; Lisp_Object Qbeginning_of_buffer, Qend_of_buffer, Qbuffer_read_only; -Lisp_Object Qintegerp, Qnatnump, Qsymbolp, Qkeywordp; +Lisp_Object Qintegerp, Qnatnump, Qsymbolp; Lisp_Object Qlistp, Qtrue_list_p, Qweak_listp; Lisp_Object Qconsp, Qsubrp; Lisp_Object Qcharacterp, Qstringp, Qarrayp, Qsequencep, Qvectorp; Lisp_Object Qchar_or_string_p, Qmarkerp, Qinteger_or_marker_p, Qbufferp; Lisp_Object Qinteger_or_char_p, Qinteger_char_or_marker_p; -Lisp_Object Qnumberp, Qnumber_or_marker_p, Qnumber_char_or_marker_p; -Lisp_Object Qbit_vectorp, Qbitp, Qcons, Qkeyword, Qcdr, Qignore; +Lisp_Object Qnumberp, Qnumber_char_or_marker_p; +Lisp_Object Qbit_vectorp, Qbitp, Qcdr; Lisp_Object Qfloatp; @@ -147,7 +147,7 @@ } void -check_int_range (int val, int min, int max) +check_int_range (EMACS_INT val, EMACS_INT min, EMACS_INT max) { if (val < min || val > max) args_out_of_range_3 (make_int (val), make_int (min), make_int (max)); @@ -160,8 +160,8 @@ /* On a few machines, XINT can only be done by calling this. */ /* XEmacs: only used by m/convex.h */ -int sign_extend_lisp_int (EMACS_INT num); -int +EMACS_INT sign_extend_lisp_int (EMACS_INT num); +EMACS_INT sign_extend_lisp_int (EMACS_INT num) { if (num & (1L << (VALBITS - 1))) @@ -615,7 +615,6 @@ if (!CONSP (conscell)) conscell = wrong_type_argument (Qconsp, conscell); - CHECK_LISP_WRITEABLE (conscell); XCAR (conscell) = newcar; return newcar; } @@ -628,7 +627,6 @@ if (!CONSP (conscell)) conscell = wrong_type_argument (Qconsp, conscell); - CHECK_LISP_WRITEABLE (conscell); XCDR (conscell) = newcdr; return newcdr; } @@ -689,7 +687,7 @@ */ (array, index_)) { - int idx; + EMACS_INT idx; retry: @@ -743,7 +741,7 @@ */ (array, index_, newval)) { - int idx; + EMACS_INT idx; retry: @@ -757,8 +755,6 @@ if (idx < 0) goto range_error; - CHECK_LISP_WRITEABLE (array); - if (VECTORP (array)) { if (idx >= XVECTOR_LENGTH (array)) goto range_error; @@ -839,7 +835,7 @@ } } -static int +static EMACS_INT integer_char_or_marker_to_int (Lisp_Object obj) { retry: @@ -1416,8 +1412,8 @@ */ (num1, num2)) { - int ival1 = integer_char_or_marker_to_int (num1); - int ival2 = integer_char_or_marker_to_int (num2); + EMACS_INT ival1 = integer_char_or_marker_to_int (num1); + EMACS_INT ival2 = integer_char_or_marker_to_int (num2); if (ival2 == 0) Fsignal (Qarith_error, Qnil); @@ -1468,7 +1464,7 @@ } #endif /* LISP_FLOAT_TYPE */ { - int ival; + EMACS_INT ival; if (iod2.c.ival == 0) goto divide_by_zero; ival = iod1.c.ival % iod2.c.ival; @@ -1570,7 +1566,7 @@ static Lisp_Object encode_weak_list_type (enum weak_list_type type); static Lisp_Object -mark_weak_list (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_weak_list (Lisp_Object obj) { return Qnil; /* nichts ist gemarkt */ } @@ -1625,7 +1621,7 @@ static const struct lrecord_description weak_list_description[] = { { XD_LISP_OBJECT, offsetof(struct weak_list, list), 1 }, - { XD_LISP_OBJECT, offsetof(struct weak_list, next_weak), 1 }, + { XD_LO_LINK, offsetof(struct weak_list, next_weak) }, { XD_END } }; @@ -1652,20 +1648,19 @@ */ int -finish_marking_weak_lists (int (*obj_marked_p) (Lisp_Object), - void (*markobj) (Lisp_Object)) +finish_marking_weak_lists (void) { Lisp_Object rest; int did_mark = 0; for (rest = Vall_weak_lists; - !GC_NILP (rest); + !NILP (rest); rest = XWEAK_LIST (rest)->next_weak) { Lisp_Object rest2; enum weak_list_type type = XWEAK_LIST (rest)->type; - if (! obj_marked_p (rest)) + if (! marked_p (rest)) /* The weak list is probably garbage. Ignore it. */ continue; @@ -1673,7 +1668,7 @@ /* We need to be trickier since we're inside of GC; use CONSP instead of !NILP in case of user-visible imperfect lists */ - GC_CONSP (rest2); + CONSP (rest2); rest2 = XCDR (rest2)) { Lisp_Object elem; @@ -1688,7 +1683,7 @@ (either because of an external pointer or because of a previous call to this function), and likewise for all the rest of the elements in the list, so we can stop now. */ - if (obj_marked_p (rest2)) + if (marked_p (rest2)) break; elem = XCAR (rest2); @@ -1696,19 +1691,19 @@ switch (type) { case WEAK_LIST_SIMPLE: - if (obj_marked_p (elem)) + if (marked_p (elem)) need_to_mark_cons = 1; break; case WEAK_LIST_ASSOC: - if (!GC_CONSP (elem)) + if (!CONSP (elem)) { /* just leave bogus elements there */ need_to_mark_cons = 1; need_to_mark_elem = 1; } - else if (obj_marked_p (XCAR (elem)) && - obj_marked_p (XCDR (elem))) + else if (marked_p (XCAR (elem)) && + marked_p (XCDR (elem))) { need_to_mark_cons = 1; /* We still need to mark elem, because it's @@ -1718,13 +1713,13 @@ break; case WEAK_LIST_KEY_ASSOC: - if (!GC_CONSP (elem)) + if (!CONSP (elem)) { /* just leave bogus elements there */ need_to_mark_cons = 1; need_to_mark_elem = 1; } - else if (obj_marked_p (XCAR (elem))) + else if (marked_p (XCAR (elem))) { need_to_mark_cons = 1; /* We still need to mark elem and XCDR (elem); @@ -1734,13 +1729,13 @@ break; case WEAK_LIST_VALUE_ASSOC: - if (!GC_CONSP (elem)) + if (!CONSP (elem)) { /* just leave bogus elements there */ need_to_mark_cons = 1; need_to_mark_elem = 1; } - else if (obj_marked_p (XCDR (elem))) + else if (marked_p (XCDR (elem))) { need_to_mark_cons = 1; /* We still need to mark elem and XCAR (elem); @@ -1753,23 +1748,23 @@ abort (); } - if (need_to_mark_elem && ! obj_marked_p (elem)) + if (need_to_mark_elem && ! marked_p (elem)) { - markobj (elem); + mark_object (elem); did_mark = 1; } /* We also need to mark the cons that holds the elem or - assoc-pair. We do *not* want to call (markobj) here + assoc-pair. We do *not* want to call (mark_object) here because that will mark the entire list; we just want to mark the cons itself. */ if (need_to_mark_cons) { - struct Lisp_Cons *ptr = XCONS (rest2); - if (!CONS_MARKED_P (ptr)) + Lisp_Cons *c = XCONS (rest2); + if (!CONS_MARKED_P (c)) { - MARK_CONS (ptr); + MARK_CONS (c); did_mark = 1; } } @@ -1777,9 +1772,9 @@ /* In case of imperfect list, need to mark the final cons because we're not removing it */ - if (!GC_NILP (rest2) && ! obj_marked_p (rest2)) + if (!NILP (rest2) && ! marked_p (rest2)) { - markobj (rest2); + mark_object (rest2); did_mark = 1; } } @@ -1788,18 +1783,18 @@ } void -prune_weak_lists (int (*obj_marked_p) (Lisp_Object)) +prune_weak_lists (void) { Lisp_Object rest, prev = Qnil; for (rest = Vall_weak_lists; - !GC_NILP (rest); + !NILP (rest); rest = XWEAK_LIST (rest)->next_weak) { - if (! (obj_marked_p (rest))) + if (! (marked_p (rest))) { /* This weak list itself is garbage. Remove it from the list. */ - if (GC_NILP (prev)) + if (NILP (prev)) Vall_weak_lists = XWEAK_LIST (rest)->next_weak; else XWEAK_LIST (prev)->next_weak = @@ -1815,7 +1810,7 @@ /* We need to be trickier since we're inside of GC; use CONSP instead of !NILP in case of user-visible imperfect lists */ - GC_CONSP (rest2);) + CONSP (rest2);) { /* It suffices to check the cons for marking, regardless of the type of weak list: @@ -1826,10 +1821,10 @@ have been marked in finish_marking_weak_lists(). -- otherwise, it's not marked and should disappear. */ - if (! obj_marked_p (rest2)) + if (! marked_p (rest2)) { /* bye bye :-( */ - if (GC_NILP (prev2)) + if (NILP (prev2)) XWEAK_LIST (rest)->list = XCDR (rest2); else XCDR (prev2) = XCDR (rest2); @@ -1870,7 +1865,7 @@ if (go_tortoise) tortoise = XCDR (tortoise); go_tortoise = !go_tortoise; - if (GC_EQ (rest2, tortoise)) + if (EQ (rest2, tortoise)) break; } } @@ -2081,17 +2076,13 @@ void syms_of_data (void) { - defsymbol (&Qcons, "cons"); - defsymbol (&Qkeyword, "keyword"); defsymbol (&Qquote, "quote"); defsymbol (&Qlambda, "lambda"); - defsymbol (&Qignore, "ignore"); defsymbol (&Qlistp, "listp"); defsymbol (&Qtrue_list_p, "true-list-p"); defsymbol (&Qconsp, "consp"); defsymbol (&Qsubrp, "subrp"); defsymbol (&Qsymbolp, "symbolp"); - defsymbol (&Qkeywordp, "keywordp"); defsymbol (&Qintegerp, "integerp"); defsymbol (&Qcharacterp, "characterp"); defsymbol (&Qnatnump, "natnump"); @@ -2108,7 +2099,6 @@ defsymbol (&Qinteger_or_char_p, "integer-or-char-p"); defsymbol (&Qinteger_char_or_marker_p, "integer-char-or-marker-p"); defsymbol (&Qnumberp, "numberp"); - defsymbol (&Qnumber_or_marker_p, "number-or-marker-p"); defsymbol (&Qnumber_char_or_marker_p, "number-char-or-marker-p"); defsymbol (&Qcdr, "cdr"); defsymbol (&Qweak_listp, "weak-list-p"); @@ -2207,6 +2197,7 @@ { /* This must not be staticpro'd */ Vall_weak_lists = Qnil; + pdump_wire_list (&Vall_weak_lists); #ifdef DEBUG_XEMACS DEFVAR_BOOL ("debug-issue-ebola-notices", &debug_issue_ebola_notices /* diff -r 28d9c139be4c -r 11054d720c21 src/database.c --- a/src/database.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/database.c Mon Aug 13 11:26:11 2007 +0200 @@ -148,12 +148,10 @@ } static Lisp_Object -mark_database (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_database (Lisp_Object obj) { Lisp_Database *db = XDATABASE (obj); - - markobj (db->fname); - return Qnil; + return db->fname; } static void diff -r 28d9c139be4c -r 11054d720c21 src/debug.c --- a/src/debug.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/debug.c Mon Aug 13 11:26:11 2007 +0200 @@ -39,8 +39,7 @@ * 4. Add a FROB line for it in xemacs_debug_loop. */ -Lisp_Object Qredisplay, Qbuffers, Qfaces; -Lisp_Object Qwindows, Qframes, Qdevices; +static Lisp_Object Qredisplay, Qbuffers, Qfaces, Qwindows, Qframes, Qdevices; struct debug_classes active_debug_classes; @@ -194,7 +193,6 @@ defsymbol (&Qwindows, "windows"); defsymbol (&Qframes, "frames"); defsymbol (&Qdevices, "devices"); - /* defsymbol (&Qbyte_code, "byte-code"); in bytecode.c */ DEFSUBR (Fadd_debug_class_to_check); DEFSUBR (Fdelete_debug_class_to_check); @@ -206,7 +204,7 @@ } void -vars_of_debug (void) +reinit_vars_of_debug (void) { /* If you need to have any classes active early on in startup, then the flags should be set here. @@ -214,3 +212,9 @@ to emacs.c. */ xemacs_debug_loop (INIT, Qnil, Qnil); } + +void +vars_of_debug (void) +{ + reinit_vars_of_debug (); +} diff -r 28d9c139be4c -r 11054d720c21 src/debug.h --- a/src/debug.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/debug.h Mon Aug 13 11:26:11 2007 +0200 @@ -53,8 +53,6 @@ unsigned int types_of_byte_code; }; -extern Lisp_Object Qbuffers, Qdevices, Qfaces, Qframes, Qredisplay, Qwindows; - extern struct debug_classes active_debug_classes; #define DASSERT(class, desired_type, action, assertion) do \ diff -r 28d9c139be4c -r 11054d720c21 src/depend --- a/src/depend Mon Aug 13 11:25:03 2007 +0200 +++ b/src/depend Mon Aug 13 11:26:11 2007 +0200 @@ -35,7 +35,7 @@ menubar-x.o: $(LISP_H) $(LWLIB_SRCDIR)/lwlib.h EmacsFrame.h buffer.h bufslots.h commands.h conslots.h console-x.h console.h device.h events.h frame.h frameslots.h glyphs.h gui-x.h gui.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h opaque.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h systime.h toolbar.h window.h winslots.h xintrinsic.h objects-x.o: $(LISP_H) buffer.h bufslots.h conslots.h console-x.h console.h device.h insdel.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h objects-x.h objects.h specifier.h symeval.h symsinit.h xintrinsic.h redisplay-x.o: $(LISP_H) $(LWLIB_SRCDIR)/lwlib.h EmacsFrame.h EmacsFrameP.h buffer.h bufslots.h conslots.h console-x.h console.h debug.h device.h faces.h file-coding.h frame.h frameslots.h glyphs-x.h glyphs.h gui.h gutter.h lisp-disunion.h lisp-union.h lrecord.h mule-ccl.h mule-charset.h objects-x.h objects.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h sysdep.h sysproc.h systime.h toolbar.h window.h winslots.h xgccache.h xintrinsic.h xintrinsicp.h xmprimitivep.h -scrollbar-x.o: $(LISP_H) $(LWLIB_SRCDIR)/lwlib.h conslots.h console-x.h console.h device.h frame.h frameslots.h glyphs-x.h glyphs.h gui-x.h gui.h lisp-disunion.h lisp-union.h lrecord.h redisplay.h scrollbar-x.h scrollbar.h specifier.h symeval.h symsinit.h toolbar.h window.h winslots.h xintrinsic.h +scrollbar-x.o: $(LISP_H) $(LWLIB_SRCDIR)/lwlib.h EmacsFrame.h conslots.h console-x.h console.h device.h frame.h frameslots.h glyphs-x.h glyphs.h gui-x.h gui.h lisp-disunion.h lisp-union.h lrecord.h redisplay.h scrollbar-x.h scrollbar.h specifier.h symeval.h symsinit.h toolbar.h window.h winslots.h xintrinsic.h select-x.o: $(LISP_H) buffer.h bufslots.h conslots.h console-x.h console.h device.h frame.h frameslots.h glyphs.h gui.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h objects-x.h objects.h opaque.h redisplay.h scrollbar.h select.h specifier.h symeval.h symsinit.h systime.h toolbar.h xintrinsic.h toolbar-x.o: $(LISP_H) $(LWLIB_SRCDIR)/lwlib.h EmacsFrame.h EmacsFrameP.h buffer.h bufslots.h conslots.h console-x.h console.h device.h faces.h frame.h frameslots.h glyphs-x.h glyphs.h gui.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h objects-x.h objects.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h toolbar.h window.h winslots.h xintrinsic.h xintrinsicp.h xmprimitivep.h #endif @@ -45,7 +45,7 @@ #ifdef MULE mule-canna.o: $(LISP_H) buffer.h bufslots.h file-coding.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h symeval.h symsinit.h mule-ccl.o: $(LISP_H) buffer.h bufslots.h file-coding.h lisp-disunion.h lisp-union.h lrecord.h mule-ccl.h mule-charset.h symeval.h symsinit.h -mule-charset.o: $(LISP_H) buffer.h bufslots.h chartab.h conslots.h console.h device.h elhash.h faces.h lisp-disunion.h lisp-union.h lrecord.h lstream.h mule-charset.h symeval.h symsinit.h +mule-charset.o: $(LISP_H) buffer.h bufslots.h chartab.h conslots.h console.h device.h elhash.h faces.h lisp-disunion.h lisp-union.h lrecord.h lstream.h mule-ccl.h mule-charset.h symeval.h symsinit.h mule-mcpath.o: $(LISP_H) buffer.h bufslots.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h symeval.h symsinit.h sysfile.h mule-wnnfns.o: $(LISP_H) buffer.h bufslots.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h redisplay.h scrollbar.h symeval.h symsinit.h sysdep.h window.h winslots.h mule.o: $(LISP_H) lisp-disunion.h lisp-union.h lrecord.h regex.h symeval.h symsinit.h @@ -119,7 +119,7 @@ gif_io.o: gifrlib.h glyphs-eimage.o: $(LISP_H) buffer.h bufslots.h conslots.h console.h device.h faces.h file-coding.h frame.h frameslots.h gifrlib.h glyphs.h gui.h lisp-disunion.h lisp-union.h lrecord.h lstream.h mule-charset.h objects.h opaque.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h sysfile.h toolbar.h glyphs-widget.o: $(LISP_H) buffer.h bufslots.h bytecode.h conslots.h console.h device.h faces.h frame.h frameslots.h glyphs.h gui.h insdel.h lisp-disunion.h lisp-union.h lrecord.h lstream.h mule-charset.h objects.h opaque.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h toolbar.h window.h winslots.h -glyphs.o: $(LISP_H) buffer.h bufslots.h chartab.h conslots.h console.h device.h elhash.h faces.h frame.h frameslots.h glyphs.h gui.h insdel.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h objects.h opaque.h rangetab.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h toolbar.h window.h winslots.h +glyphs.o: $(LISP_H) blocktype.h buffer.h bufslots.h chartab.h conslots.h console.h device.h elhash.h faces.h frame.h frameslots.h glyphs.h gui.h insdel.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h objects.h opaque.h rangetab.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h toolbar.h window.h winslots.h gmalloc.o: config.h getpagesize.h gpmevent.o: $(LISP_H) conslots.h console-tty.h console.h device.h events-mod.h events.h gpmevent.h lisp-disunion.h lisp-union.h lrecord.h symeval.h symsinit.h sysdep.h syssignal.h systime.h systty.h gui.o: $(LISP_H) bytecode.h elhash.h gui.h lisp-disunion.h lisp-union.h lrecord.h symeval.h symsinit.h @@ -166,7 +166,7 @@ redisplay-tty.o: $(LISP_H) buffer.h bufslots.h conslots.h console-tty.h console.h device.h events.h faces.h frame.h frameslots.h glyphs.h gui.h lisp-disunion.h lisp-union.h lrecord.h lstream.h mule-charset.h objects-tty.h objects.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h sysdep.h syssignal.h systime.h systty.h toolbar.h window.h winslots.h redisplay.o: $(LISP_H) buffer.h bufslots.h commands.h conslots.h console-tty.h console.h debug.h device.h elhash.h extents.h faces.h file-coding.h frame.h frameslots.h glyphs.h gui.h gutter.h insdel.h line-number.h lisp-disunion.h lisp-union.h lrecord.h menubar.h mule-charset.h objects.h process.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h syssignal.h systty.h toolbar.h window.h winslots.h regex.o: $(LISP_H) buffer.h bufslots.h chartab.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h regex.h symeval.h symsinit.h syntax.h -scrollbar.o: $(LISP_H) buffer.h bufslots.h commands.h conslots.h console.h device.h frame.h frameslots.h glyphs.h gui.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h toolbar.h window.h winslots.h +scrollbar.o: $(LISP_H) buffer.h bufslots.h commands.h conslots.h console.h device.h frame.h frameslots.h glyphs.h gui.h gutter.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h redisplay.h scrollbar.h specifier.h symeval.h symsinit.h toolbar.h window.h winslots.h search.o: $(LISP_H) buffer.h bufslots.h chartab.h insdel.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h opaque.h regex.h symeval.h symsinit.h syntax.h select.o: $(LISP_H) buffer.h bufslots.h conslots.h console.h device.h frame.h frameslots.h glyphs.h gui.h lisp-disunion.h lisp-union.h lrecord.h mule-charset.h objects.h opaque.h redisplay.h scrollbar.h select.h specifier.h symeval.h symsinit.h toolbar.h sgiplay.o: $(LISP_H) libst.h lisp-disunion.h lisp-union.h lrecord.h symeval.h symsinit.h diff -r 28d9c139be4c -r 11054d720c21 src/device-msw.c --- a/src/device-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/device-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -139,7 +139,9 @@ wc.lpfnWndProc = (WNDPROC) mswindows_wnd_proc; wc.cbClsExtra = 0; wc.cbWndExtra = MSWINDOWS_WINDOW_EXTRA_BYTES; - wc.hInstance = NULL; /* ? */ + /* This must match whatever is passed to CreateWIndowEx, NULL is ok + for this. */ + wc.hInstance = NULL; wc.hIcon = LoadIcon (GetModuleHandle(NULL), XEMACS_CLASS); wc.hCursor = LoadCursor (NULL, IDC_ARROW); /* Background brush is only used during sizing, when XEmacs cannot @@ -151,6 +153,17 @@ wc.hIconSm = LoadImage (GetModuleHandle (NULL), XEMACS_CLASS, IMAGE_ICON, 16, 16, 0); RegisterClassEx (&wc); + +#ifdef HAVE_WIDGETS + xzero (wc); + /* Register the main window class */ + wc.cbSize = sizeof (WNDCLASSEX); + wc.lpfnWndProc = (WNDPROC) mswindows_control_wnd_proc; + wc.lpszClassName = XEMACS_CONTROL_CLASS; + wc.hInstance = NULL; + RegisterClassEx (&wc); +#endif + #ifdef HAVE_TOOLBARS InitCommonControls (); #endif diff -r 28d9c139be4c -r 11054d720c21 src/device-x.c --- a/src/device-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/device-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -743,10 +743,10 @@ } static void -x_mark_device (struct device *d, void (*markobj) (Lisp_Object)) +x_mark_device (struct device *d) { - markobj (DEVICE_X_WM_COMMAND_FRAME (d)); - markobj (DEVICE_X_DATA (d)->x_keysym_map_hash_table); + mark_object (DEVICE_X_WM_COMMAND_FRAME (d)); + mark_object (DEVICE_X_DATA (d)->x_keysym_map_hash_table); } @@ -1893,29 +1893,43 @@ } void +reinit_console_type_create_device_x (void) +{ + /* Initialize variables to speed up X resource interactions */ + CONST char *valid_resource_chars = + "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_"; + while (*valid_resource_chars) + valid_resource_char_p[(unsigned int) (*valid_resource_chars++)] = 1; + + name_char_dynarr = Dynarr_new (char); + class_char_dynarr = Dynarr_new (char); +} + +void console_type_create_device_x (void) { + reinit_console_type_create_device_x (); CONSOLE_HAS_METHOD (x, init_device); CONSOLE_HAS_METHOD (x, finish_init_device); CONSOLE_HAS_METHOD (x, mark_device); CONSOLE_HAS_METHOD (x, delete_device); CONSOLE_HAS_METHOD (x, device_system_metrics); +} - { - /* Initialize variables to speed up X resource interactions */ - CONST char *valid_resource_chars = - "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_"; - while (*valid_resource_chars) - valid_resource_char_p[(unsigned int) (*valid_resource_chars++)] = 1; +void +reinit_vars_of_device_x (void) +{ + error_expected = 0; + error_occurred = 0; - name_char_dynarr = Dynarr_new (char); - class_char_dynarr = Dynarr_new (char); - } + in_resource_setting = 0; } void vars_of_device_x (void) { + reinit_vars_of_device_x (); + DEFVAR_LISP ("x-emacs-application-class", &Vx_emacs_application_class /* The X application class of the XEmacs process. This controls, among other things, the name of the `app-defaults' file @@ -1958,9 +1972,4 @@ staticpro (&Vdefault_x_device); Vdefault_x_device = Qnil; - - error_expected = 0; - error_occurred = 0; - - in_resource_setting = 0; } diff -r 28d9c139be4c -r 11054d720c21 src/device.c --- a/src/device.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/device.c Mon Aug 13 11:26:11 2007 +0200 @@ -73,41 +73,40 @@ Qslow_device, Qsecurity; Lisp_Object Qdevicep, Qdevice_live_p; -Lisp_Object Qdelete_device; Lisp_Object Qcreate_device_hook; Lisp_Object Qdelete_device_hook; Lisp_Object Vdevice_class_list; static Lisp_Object -mark_device (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_device (Lisp_Object obj) { struct device *d = XDEVICE (obj); - markobj (d->name); - markobj (d->connection); - markobj (d->canon_connection); - markobj (d->console); - markobj (d->selected_frame); - markobj (d->frame_with_focus_real); - markobj (d->frame_with_focus_for_hooks); - markobj (d->frame_that_ought_to_have_focus); - markobj (d->device_class); - markobj (d->user_defined_tags); - markobj (d->pixel_to_glyph_cache.obj1); - markobj (d->pixel_to_glyph_cache.obj2); + mark_object (d->name); + mark_object (d->connection); + mark_object (d->canon_connection); + mark_object (d->console); + mark_object (d->selected_frame); + mark_object (d->frame_with_focus_real); + mark_object (d->frame_with_focus_for_hooks); + mark_object (d->frame_that_ought_to_have_focus); + mark_object (d->device_class); + mark_object (d->user_defined_tags); + mark_object (d->pixel_to_glyph_cache.obj1); + mark_object (d->pixel_to_glyph_cache.obj2); - markobj (d->color_instance_cache); - markobj (d->font_instance_cache); + mark_object (d->color_instance_cache); + mark_object (d->font_instance_cache); #ifdef MULE - markobj (d->charset_font_cache); + mark_object (d->charset_font_cache); #endif - markobj (d->image_instance_cache); + mark_object (d->image_instance_cache); if (d->devmeths) { - markobj (d->devmeths->symbol); - MAYBE_DEVMETH (d, mark_device, (d, markobj)); + mark_object (d->devmeths->symbol); + MAYBE_DEVMETH (d, mark_device, (d)); } return (d->frame_list); @@ -1250,7 +1249,6 @@ defsymbol (&Qdevicep, "devicep"); defsymbol (&Qdevice_live_p, "device-live-p"); - defsymbol (&Qdelete_device, "delete-device"); defsymbol (&Qcreate_device_hook, "create-device-hook"); defsymbol (&Qdelete_device_hook, "delete-device-hook"); @@ -1299,8 +1297,18 @@ } void +reinit_vars_of_device (void) +{ + staticpro_nodump (&Vdefault_device); + Vdefault_device = Qnil; + asynch_device_change_pending = 0; +} + +void vars_of_device (void) { + reinit_vars_of_device (); + DEFVAR_LISP ("create-device-hook", &Vcreate_device_hook /* Function or functions to call when a device is created. One argument, the newly-created device. @@ -1316,11 +1324,6 @@ */ ); Vdelete_device_hook = Qnil; - staticpro (&Vdefault_device); - Vdefault_device = Qnil; - - asynch_device_change_pending = 0; - Vdevice_class_list = list3 (Qcolor, Qgrayscale, Qmono); staticpro (&Vdevice_class_list); diff -r 28d9c139be4c -r 11054d720c21 src/device.h --- a/src/device.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/device.h Mon Aug 13 11:26:11 2007 +0200 @@ -168,6 +168,7 @@ unsigned int frame_changed :1; unsigned int glyphs_changed :1; unsigned int subwindows_changed :1; + unsigned int subwindows_state_changed :1; unsigned int icon_changed :1; unsigned int menubar_changed :1; unsigned int modeline_changed :1; @@ -220,7 +221,6 @@ #define XDEVICE(x) XRECORD (x, device, struct device) #define XSETDEVICE(x, p) XSETRECORD (x, p, device) #define DEVICEP(x) RECORDP (x, device) -#define GC_DEVICEP(x) GC_RECORDP (x, device) #define CHECK_DEVICE(x) CHECK_RECORD (x, device) #define CONCHECK_DEVICE(x) CONCHECK_RECORD (x, device) @@ -247,7 +247,7 @@ return d; } # define DEVICE_TYPE_DATA(d, type) \ - ((struct type##_device *) (error_check_device_type (d, Q##type))->device_data) + ((struct type##_device *) error_check_device_type (d, Q##type)->device_data) #else # define DEVICE_TYPE_DATA(d, type) \ ((struct type##_device *) (d)->device_data) @@ -348,6 +348,9 @@ #define MARK_DEVICE_SUBWINDOWS_CHANGED(d) \ ((void) (subwindows_changed = (d)->subwindows_changed = 1)) +#define MARK_DEVICE_SUBWINDOWS_STATE_CHANGED(d) \ + ((void) (subwindows_state_changed = (d)->subwindows_state_changed = 1)) + #define MARK_DEVICE_TOOLBARS_CHANGED(d) \ ((void) (toolbar_changed = (d)->toolbar_changed = 1)) @@ -365,6 +368,14 @@ MARK_DEVICE_FACES_CHANGED (mdffc_d); \ } while (0) +#define MARK_DEVICE_FRAMES_GLYPHS_CHANGED(d) do { \ + struct device *mdffc_d = (d); \ + Lisp_Object frmcons; \ + DEVICE_FRAME_LOOP (frmcons, mdffc_d) \ + XFRAME (XCAR (frmcons))->glyphs_changed = 1; \ + MARK_DEVICE_GLYPHS_CHANGED (mdffc_d); \ +} while (0) + #define MARK_DEVICE_FRAME_CHANGED(d) \ ((void) (frame_changed = (d)->frame_changed = 1)) diff -r 28d9c139be4c -r 11054d720c21 src/dired.c --- a/src/dired.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/dired.c Mon Aug 13 11:26:11 2007 +0200 @@ -558,7 +558,7 @@ } struct user_cache { - char **data; + Bufbyte **data; int length; int size; EMACS_TIME last_rebuild_time; @@ -634,9 +634,10 @@ Bufbyte *pwuser; QUIT; DO_REALLOC (user_cache.data, user_cache.size, - user_cache.length + 1, char *); + user_cache.length + 1, Bufbyte *); GET_C_CHARPTR_INT_DATA_ALLOCA (pwd->pw_name, FORMAT_OS, pwuser); - user_cache.data[user_cache.length++] = xstrdup (pwuser); + user_cache.data[user_cache.length++] = + (Bufbyte *) xstrdup ((char *) pwuser); } endpwent (); speed_up_interrupts (); diff -r 28d9c139be4c -r 11054d720c21 src/doprnt.c --- a/src/doprnt.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/doprnt.c Mon Aug 13 11:26:11 2007 +0200 @@ -386,7 +386,7 @@ if (strchr (int_converters, ch)) { if (spec->h_flag) - arg.i = va_arg (vargs, short); + arg.i = va_arg (vargs, int /* short */); else if (spec->l_flag) arg.l = va_arg (vargs, long); else @@ -395,7 +395,7 @@ else if (strchr (unsigned_int_converters, ch)) { if (spec->h_flag) - arg.ui = va_arg (vargs, unsigned short); + arg.ui = va_arg (vargs, unsigned int /* unsigned short */); else if (spec->l_flag) arg.ul = va_arg (vargs, unsigned long); else diff -r 28d9c139be4c -r 11054d720c21 src/dynarr.c --- a/src/dynarr.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/dynarr.c Mon Aug 13 11:26:11 2007 +0200 @@ -111,6 +111,19 @@ int Dynarr_min_size = 1; +static void +Dynarr_realloc (Dynarr *dy, int new_size) +{ + if (DUMPEDP (dy->base)) + { + void *new_base = malloc (new_size); + memcpy (new_base, dy->base, dy->max > new_size ? new_size : dy->max); + dy->base = new_base; + } + else + dy->base = xrealloc (dy->base, new_size); +} + void * Dynarr_newf (int elsize) { @@ -138,7 +151,7 @@ /* Don't do anything if the array is already big enough. */ if (newsize > dy->max) { - dy->base = xrealloc (dy->base, newsize*dy->elsize); + Dynarr_realloc (dy, newsize*dy->elsize); dy->max = newsize; } } @@ -186,9 +199,10 @@ { Dynarr *dy = (Dynarr *) d; - if (dy->base) + if (dy->base && !DUMPEDP (dy->base)) xfree (dy->base); - xfree (dy); + if(!DUMPEDP (dy)) + xfree (dy); } #ifdef MEMORY_USAGE_STATS diff -r 28d9c139be4c -r 11054d720c21 src/editfns.c --- a/src/editfns.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/editfns.c Mon Aug 13 11:26:11 2007 +0200 @@ -45,6 +45,7 @@ #include "systime.h" #include "sysdep.h" #include "syspwd.h" +#include "sysfile.h" /* for getcwd */ /* Some static data, and a function to initialize it for each run */ diff -r 28d9c139be4c -r 11054d720c21 src/eldap.c --- a/src/eldap.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/eldap.c Mon Aug 13 11:26:11 2007 +0200 @@ -47,14 +47,13 @@ Lisp_Object Qldapp; /* ldap-open plist keywords */ -extern Lisp_Object Qport, Qauth, Qbinddn, Qpasswd, Qderef, Qtimelimit, - Qsizelimit; +static Lisp_Object Qport, Qauth, Qbinddn, Qpasswd, Qderef, Qtimelimit, Qsizelimit; /* Search scope limits */ -extern Lisp_Object Qbase, Qonelevel, Qsubtree; +static Lisp_Object Qbase, Qonelevel, Qsubtree; /* Authentication methods */ -extern Lisp_Object Qkrbv41, Qkrbv42; +static Lisp_Object Qkrbv41, Qkrbv42; /* Deref policy */ -extern Lisp_Object Qnever, Qalways, Qfind; +static Lisp_Object Qnever, Qalways, Qfind; /************************************************************************/ /* Utility Functions */ @@ -98,7 +97,7 @@ } static Lisp_Object -mark_ldap (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_ldap (Lisp_Object obj) { return XLDAP (obj)->host; } @@ -579,6 +578,22 @@ syms_of_eldap (void) { defsymbol (&Qldapp, "ldapp"); + defsymbol (&Qport, "port"); + defsymbol (&Qauth, "auth"); + defsymbol (&Qbinddn, "binddn"); + defsymbol (&Qpasswd, "passwd"); + defsymbol (&Qderef, "deref"); + defsymbol (&Qtimelimit, "timelimit"); + defsymbol (&Qsizelimit, "sizelimit"); + defsymbol (&Qbase, "base"); + defsymbol (&Qonelevel, "onelevel"); + defsymbol (&Qsubtree, "subtree"); + defsymbol (&Qkrbv41, "krbv41"); + defsymbol (&Qkrbv42, "krbv42"); + defsymbol (&Qnever, "never"); + defsymbol (&Qalways, "always"); + defsymbol (&Qfind, "find"); + DEFSUBR (Fldapp); DEFSUBR (Fldap_host); DEFSUBR (Fldap_status); diff -r 28d9c139be4c -r 11054d720c21 src/eldap.h --- a/src/eldap.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/eldap.h Mon Aug 13 11:26:11 2007 +0200 @@ -44,7 +44,6 @@ #define XLDAP(x) XRECORD (x, ldap, struct Lisp_LDAP) #define XSETLDAP(x, p) XSETRECORD (x, p, ldap) #define LDAPP(x) RECORDP (x, ldap) -#define GC_LDAPP(x) GC_RECORDP (x, ldap) #define CHECK_LDAP(x) CHECK_RECORD (x, ldap) #define CONCHECK_LDAP(x) CONCHECK_RECORD (x, ldap) diff -r 28d9c139be4c -r 11054d720c21 src/elhash.c --- a/src/elhash.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/elhash.c Mon Aug 13 11:26:11 2007 +0200 @@ -27,11 +27,15 @@ #include "bytecode.h" #include "elhash.h" -Lisp_Object Qhash_tablep, Qhashtable, Qhash_table; -Lisp_Object Qweak, Qkey_weak, Qvalue_weak, Qnon_weak; +Lisp_Object Qhash_tablep; +static Lisp_Object Qhashtable, Qhash_table; +static Lisp_Object Qweakness, Qvalue; static Lisp_Object Vall_weak_hash_tables; static Lisp_Object Qrehash_size, Qrehash_threshold; -static Lisp_Object Q_size, Q_test, Q_type, Q_rehash_size, Q_rehash_threshold; +static Lisp_Object Q_size, Q_test, Q_weakness, Q_rehash_size, Q_rehash_threshold; + +/* obsolete as of 19990901 in xemacs-21.2 */ +static Lisp_Object Qweak, Qkey_weak, Qvalue_weak, Qnon_weak, Q_type; typedef struct hentry { @@ -51,14 +55,16 @@ hash_table_hash_function_t hash_function; hash_table_test_function_t test_function; hentry *hentries; - enum hash_table_type type; /* whether and how this hash table is weak */ + enum hash_table_weakness weakness; Lisp_Object next_weak; /* Used to chain together all of the weak hash tables. Don't mark through this. */ }; typedef struct Lisp_Hash_Table Lisp_Hash_Table; #define HENTRY_CLEAR_P(hentry) ((*(EMACS_UINT*)(&((hentry)->key))) == 0) -#define CLEAR_HENTRY(hentry) ((*(EMACS_UINT*)(&((hentry)->key))) = 0) +#define CLEAR_HENTRY(hentry) \ + ((*(EMACS_UINT*)(&((hentry)->key))) = 0, \ + (*(EMACS_UINT*)(&((hentry)->value))) = 0) #define HASH_TABLE_DEFAULT_SIZE 16 #define HASH_TABLE_DEFAULT_REHASH_SIZE 1.3 @@ -190,29 +196,29 @@ static Lisp_Object -mark_hash_table (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_hash_table (Lisp_Object obj) { Lisp_Hash_Table *ht = XHASH_TABLE (obj); /* If the hash table is weak, we don't want to mark the keys and values (we scan over them after everything else has been marked, and mark or remove them as necessary). */ - if (ht->type == HASH_TABLE_NON_WEAK) + if (ht->weakness == HASH_TABLE_NON_WEAK) { hentry *e, *sentinel; for (e = ht->hentries, sentinel = e + ht->size; e < sentinel; e++) if (!HENTRY_CLEAR_P (e)) { - markobj (e->key); - markobj (e->value); + mark_object (e->key); + mark_object (e->value); } } return Qnil; } /* Equality of hash tables. Two hash tables are equal when they are of - the same type and test function, they have the same number of + the same weakness and test function, they have the same number of elements, and for each key in the hash table, the values are `equal'. This is similar to Common Lisp `equalp' of hash tables, with the @@ -229,7 +235,7 @@ hentry *e, *sentinel; if ((ht1->test_function != ht2->test_function) || - (ht1->type != ht2->type) || + (ht1->weakness != ht2->weakness) || (ht1->count != ht2->count)) return 0; @@ -256,9 +262,13 @@ #s(hash-table size 2 data (key1 value1 key2 value2)) - The supported keywords are `type' (non-weak (or nil), weak, - key-weak and value-weak), `test' (eql (or nil), eq or equal), - `size' (a natnum or nil) and `data' (a list). + The supported hash table structure keywords and their values are: + `test' (eql (or nil), eq or equal) + `size' (a natnum or nil) + `rehash-size' (a float) + `rehash-threshold' (a float) + `weakness' (nil, t, key or value) + `data' (a list) If `print-readably' is non-nil, then a simpler syntax is used; for instance: @@ -307,16 +317,6 @@ write_c_string (print_readably ? "#s(hash-table" : "#type != HASH_TABLE_NON_WEAK) - { - sprintf (buf, " type %s", - (ht->type == HASH_TABLE_WEAK ? "weak" : - ht->type == HASH_TABLE_KEY_WEAK ? "key-weak" : - ht->type == HASH_TABLE_VALUE_WEAK ? "value-weak" : - "you-d-better-not-see-this")); - write_c_string (buf, printcharfun); - } - /* These checks have a kludgy look to them, but they are safe. Due to nature of hashing, you cannot use arbitrary test functions anyway. */ @@ -340,6 +340,16 @@ write_c_string (buf, printcharfun); } + if (ht->weakness != HASH_TABLE_NON_WEAK) + { + sprintf (buf, " weakness %s", + (ht->weakness == HASH_TABLE_WEAK ? "t" : + ht->weakness == HASH_TABLE_KEY_WEAK ? "key" : + ht->weakness == HASH_TABLE_VALUE_WEAK ? "value" : + "you-d-better-not-see-this")); + write_c_string (buf, printcharfun); + } + if (ht->count) print_hash_table_data (ht, printcharfun); @@ -374,9 +384,10 @@ hentry_description_1 }; -static const struct lrecord_description hash_table_description[] = { +const struct lrecord_description hash_table_description[] = { { XD_SIZE_T, offsetof(Lisp_Hash_Table, size) }, - { XD_STRUCT_PTR, offsetof(Lisp_Hash_Table, hentries), XD_INDIRECT(0), &hentry_description }, + { XD_STRUCT_PTR, offsetof(Lisp_Hash_Table, hentries), XD_INDIRECT(0, 1), &hentry_description }, + { XD_LO_LINK, offsetof(Lisp_Hash_Table, next_weak) }, { XD_END } }; @@ -421,18 +432,18 @@ } Lisp_Object -make_general_lisp_hash_table (size_t size, - enum hash_table_type type, - enum hash_table_test test, - double rehash_size, - double rehash_threshold) +make_general_lisp_hash_table (enum hash_table_test test, + size_t size, + double rehash_size, + double rehash_threshold, + enum hash_table_weakness weakness) { Lisp_Object hash_table; Lisp_Hash_Table *ht = alloc_lcrecord_type (Lisp_Hash_Table, &lrecord_hash_table); - ht->type = type; ht->rehash_size = rehash_size; ht->rehash_threshold = rehash_threshold; + ht->weakness = weakness; switch (test) { @@ -477,7 +488,7 @@ XSETHASH_TABLE (hash_table, ht); - if (type == HASH_TABLE_NON_WEAK) + if (weakness == HASH_TABLE_NON_WEAK) ht->next_weak = Qunbound; else ht->next_weak = Vall_weak_hash_tables, Vall_weak_hash_tables = hash_table; @@ -487,11 +498,11 @@ Lisp_Object make_lisp_hash_table (size_t size, - enum hash_table_type type, + enum hash_table_weakness weakness, enum hash_table_test test) { - return make_general_lisp_hash_table (size, type, test, - HASH_TABLE_DEFAULT_REHASH_SIZE, -1.0); + return make_general_lisp_hash_table + (test, size, HASH_TABLE_DEFAULT_REHASH_SIZE, -1.0, weakness); } /* Pretty reading of hash tables. @@ -524,30 +535,40 @@ } static int -hash_table_type_validate (Lisp_Object keyword, Lisp_Object value, - Error_behavior errb) +hash_table_weakness_validate (Lisp_Object keyword, Lisp_Object value, + Error_behavior errb) { if (EQ (value, Qnil)) return 1; + if (EQ (value, Qt)) return 1; + if (EQ (value, Qkey)) return 1; + if (EQ (value, Qvalue)) return 1; + + /* Following values are obsolete as of 19990901 in xemacs-21.2 */ if (EQ (value, Qnon_weak)) return 1; if (EQ (value, Qweak)) return 1; if (EQ (value, Qkey_weak)) return 1; if (EQ (value, Qvalue_weak)) return 1; - maybe_signal_simple_error ("Invalid hash table type", + maybe_signal_simple_error ("Invalid hash table weakness", value, Qhash_table, errb); return 0; } -static enum hash_table_type -decode_hash_table_type (Lisp_Object obj) +static enum hash_table_weakness +decode_hash_table_weakness (Lisp_Object obj) { if (EQ (obj, Qnil)) return HASH_TABLE_NON_WEAK; + if (EQ (obj, Qt)) return HASH_TABLE_WEAK; + if (EQ (obj, Qkey)) return HASH_TABLE_KEY_WEAK; + if (EQ (obj, Qvalue)) return HASH_TABLE_VALUE_WEAK; + + /* Following values are obsolete as of 19990901 in xemacs-21.2 */ if (EQ (obj, Qnon_weak)) return HASH_TABLE_NON_WEAK; if (EQ (obj, Qweak)) return HASH_TABLE_WEAK; if (EQ (obj, Qkey_weak)) return HASH_TABLE_KEY_WEAK; if (EQ (obj, Qvalue_weak)) return HASH_TABLE_VALUE_WEAK; - signal_simple_error ("Invalid hash table type", obj); + signal_simple_error ("Invalid hash table weakness", obj); return HASH_TABLE_NON_WEAK; /* not reached */ } @@ -579,7 +600,7 @@ static int hash_table_rehash_size_validate (Lisp_Object keyword, Lisp_Object value, - Error_behavior errb) + Error_behavior errb) { if (!FLOATP (value)) { @@ -668,11 +689,11 @@ { Lisp_Object hash_table; Lisp_Object test = Qnil; - Lisp_Object type = Qnil; Lisp_Object size = Qnil; - Lisp_Object data = Qnil; Lisp_Object rehash_size = Qnil; Lisp_Object rehash_threshold = Qnil; + Lisp_Object weakness = Qnil; + Lisp_Object data = Qnil; while (!NILP (plist)) { @@ -681,22 +702,23 @@ value = XCAR (plist); plist = XCDR (plist); if (EQ (key, Qtest)) test = value; - else if (EQ (key, Qtype)) type = value; else if (EQ (key, Qsize)) size = value; - else if (EQ (key, Qdata)) data = value; else if (EQ (key, Qrehash_size)) rehash_size = value; else if (EQ (key, Qrehash_threshold)) rehash_threshold = value; + else if (EQ (key, Qweakness)) weakness = value; + else if (EQ (key, Qdata)) data = value; + else if (EQ (key, Qtype))/*obsolete*/ weakness = value; else abort (); } /* Create the hash table. */ hash_table = make_general_lisp_hash_table - (decode_hash_table_size (size), - decode_hash_table_type (type), - decode_hash_table_test (test), + (decode_hash_table_test (test), + decode_hash_table_size (size), decode_hash_table_rehash_size (rehash_size), - decode_hash_table_rehash_threshold (rehash_threshold)); + decode_hash_table_rehash_threshold (rehash_threshold), + decode_hash_table_weakness (weakness)); /* I'm not sure whether this can GC, but better safe than sorry. */ { @@ -723,17 +745,20 @@ struct structure_type *st; st = define_structure_type (structure_name, 0, hash_table_instantiate); + define_structure_type_keyword (st, Qtest, hash_table_test_validate); define_structure_type_keyword (st, Qsize, hash_table_size_validate); - define_structure_type_keyword (st, Qtest, hash_table_test_validate); - define_structure_type_keyword (st, Qtype, hash_table_type_validate); - define_structure_type_keyword (st, Qdata, hash_table_data_validate); define_structure_type_keyword (st, Qrehash_size, hash_table_rehash_size_validate); define_structure_type_keyword (st, Qrehash_threshold, hash_table_rehash_threshold_validate); + define_structure_type_keyword (st, Qweakness, hash_table_weakness_validate); + define_structure_type_keyword (st, Qdata, hash_table_data_validate); + + /* obsolete as of 19990901 in xemacs-21.2 */ + define_structure_type_keyword (st, Qtype, hash_table_weakness_validate); } /* Create a built-in Lisp structure type named `hash-table'. We make #s(hashtable ...) equivalent to #s(hash-table ...), - for backward comptabibility. + for backward compatibility. This is called from emacs.c. */ void structure_type_create_hash_table (void) @@ -758,17 +783,23 @@ DEFUN ("make-hash-table", Fmake_hash_table, 0, MANY, 0, /* Return a new empty hash table object. Use Common Lisp style keywords to specify hash table properties. - (make-hash-table &key :size :test :type :rehash-size :rehash-threshold) - -Keyword :size specifies the number of keys likely to be inserted. -This number of entries can be inserted without enlarging the hash table. + (make-hash-table &key test size rehash-size rehash-threshold weakness) Keyword :test can be `eq', `eql' (default) or `equal'. Comparison between keys is done using this function. If speed is important, consider using `eq'. When storing strings in the hash table, you will likely need to use `equal'. -Keyword :type can be `non-weak' (default), `weak', `key-weak' or `value-weak'. +Keyword :size specifies the number of keys likely to be inserted. +This number of entries can be inserted without enlarging the hash table. + +Keyword :rehash-size must be a float greater than 1.0, and specifies +the factor by which to increase the size of the hash table when enlarging. + +Keyword :rehash-threshold must be a float between 0.0 and 1.0, +and specifies the load factor of the hash table which triggers enlarging. + +Non-standard keyword :weakness can be `nil' (default), `t', `key' or `value'. A weak hash table is one whose pointers do not count as GC referents: for any key-value pair in the hash table, if the only remaining pointer @@ -788,58 +819,48 @@ unmarked outside of weak hash tables. The pair will remain in the hash table if the value is pointed to by something other than a weak hash table, even if the key is not. - -Keyword :rehash-size must be a float greater than 1.0, and specifies -the factor by which to increase the size of the hash table when enlarging. - -Keyword :rehash-threshold must be a float between 0.0 and 1.0, -and specifies the load factor of the hash table which triggers enlarging. - */ (int nargs, Lisp_Object *args)) { - int j = 0; + int i = 0; + Lisp_Object test = Qnil; Lisp_Object size = Qnil; - Lisp_Object type = Qnil; - Lisp_Object test = Qnil; Lisp_Object rehash_size = Qnil; Lisp_Object rehash_threshold = Qnil; - - while (j < nargs) - { - Lisp_Object keyword, value; + Lisp_Object weakness = Qnil; - keyword = args[j++]; - if (!KEYWORDP (keyword)) - signal_simple_error ("Invalid hash table property keyword", keyword); - if (j == nargs) - signal_simple_error ("Hash table property requires a value", keyword); + while (i + 1 < nargs) + { + Lisp_Object keyword = args[i++]; + Lisp_Object value = args[i++]; - value = args[j++]; - - if (EQ (keyword, Q_size)) size = value; - else if (EQ (keyword, Q_type)) type = value; - else if (EQ (keyword, Q_test)) test = value; + if (EQ (keyword, Q_test)) test = value; + else if (EQ (keyword, Q_size)) size = value; else if (EQ (keyword, Q_rehash_size)) rehash_size = value; else if (EQ (keyword, Q_rehash_threshold)) rehash_threshold = value; + else if (EQ (keyword, Q_weakness)) weakness = value; + else if (EQ (keyword, Q_type))/*obsolete*/ weakness = value; else signal_simple_error ("Invalid hash table property keyword", keyword); } + if (i < nargs) + signal_simple_error ("Hash table property requires a value", args[i]); + #define VALIDATE_VAR(var) \ if (!NILP (var)) hash_table_##var##_validate (Q##var, var, ERROR_ME); + VALIDATE_VAR (test); VALIDATE_VAR (size); - VALIDATE_VAR (type); - VALIDATE_VAR (test); VALIDATE_VAR (rehash_size); VALIDATE_VAR (rehash_threshold); + VALIDATE_VAR (weakness); return make_general_lisp_hash_table - (decode_hash_table_size (size), - decode_hash_table_type (type), - decode_hash_table_test (test), + (decode_hash_table_test (test), + decode_hash_table_size (size), decode_hash_table_rehash_size (rehash_size), - decode_hash_table_rehash_threshold (rehash_threshold)); + decode_hash_table_rehash_threshold (rehash_threshold), + decode_hash_table_weakness (weakness)); } DEFUN ("copy-hash-table", Fcopy_hash_table, 1, 1, 0, /* @@ -868,14 +889,13 @@ } static void -enlarge_hash_table (Lisp_Hash_Table *ht) +resize_hash_table (Lisp_Hash_Table *ht, size_t new_size) { hentry *old_entries, *new_entries, *old_sentinel, *new_sentinel, *e; - size_t old_size, new_size; + size_t old_size; old_size = ht->size; - new_size = ht->size = - hash_table_size ((size_t) ((double) old_size * ht->rehash_size)); + ht->size = new_size; old_entries = ht->hentries; @@ -899,7 +919,22 @@ *probe = *e; } - xfree (old_entries); + if (!DUMPEDP (old_entries)) + xfree (old_entries); +} + +void +reorganize_hash_table (Lisp_Hash_Table *ht) +{ + resize_hash_table (ht, ht->size); +} + +static void +enlarge_hash_table (Lisp_Hash_Table *ht) +{ + size_t new_size = + hash_table_size ((size_t) ((double) ht->size * ht->rehash_size)); + resize_hash_table (ht, new_size); } static hentry * @@ -955,7 +990,8 @@ remhash_1 (Lisp_Hash_Table *ht, hentry *entries, hentry *probe) { size_t size = ht->size; - CLEAR_HENTRY (probe++); + CLEAR_HENTRY (probe); + probe++; ht->count--; LINEAR_PROBING_LOOP (probe, entries, size) @@ -1016,30 +1052,6 @@ return make_int (xhash_table (hash_table)->count); } -DEFUN ("hash-table-size", Fhash_table_size, 1, 1, 0, /* -Return the size of HASH-TABLE. -This is the current number of slots in HASH-TABLE, whether occupied or not. -*/ - (hash_table)) -{ - return make_int (xhash_table (hash_table)->size); -} - -DEFUN ("hash-table-type", Fhash_table_type, 1, 1, 0, /* -Return the type of HASH-TABLE. -This can be one of `non-weak', `weak', `key-weak' or `value-weak'. -*/ - (hash_table)) -{ - switch (xhash_table (hash_table)->type) - { - case HASH_TABLE_WEAK: return Qweak; - case HASH_TABLE_KEY_WEAK: return Qkey_weak; - case HASH_TABLE_VALUE_WEAK: return Qvalue_weak; - default: return Qnon_weak; - } -} - DEFUN ("hash-table-test", Fhash_table_test, 1, 1, 0, /* Return the test function of HASH-TABLE. This can be one of `eq', `eql' or `equal'. @@ -1053,6 +1065,15 @@ Qeq); } +DEFUN ("hash-table-size", Fhash_table_size, 1, 1, 0, /* +Return the size of HASH-TABLE. +This is the current number of slots in HASH-TABLE, whether occupied or not. +*/ + (hash_table)) +{ + return make_int (xhash_table (hash_table)->size); +} + DEFUN ("hash-table-rehash-size", Fhash_table_rehash_size, 1, 1, 0, /* Return the current rehash size of HASH-TABLE. This is a float greater than 1.0; the factor by which HASH-TABLE @@ -1073,6 +1094,37 @@ return make_float (hash_table_rehash_threshold (xhash_table (hash_table))); } +DEFUN ("hash-table-weakness", Fhash_table_weakness, 1, 1, 0, /* +Return the weakness of HASH-TABLE. +This can be one of `nil', `t', `key' or `value'. +*/ + (hash_table)) +{ + switch (xhash_table (hash_table)->weakness) + { + case HASH_TABLE_WEAK: return Qt; + case HASH_TABLE_KEY_WEAK: return Qkey; + case HASH_TABLE_VALUE_WEAK: return Qvalue; + default: return Qnil; + } +} + +/* obsolete as of 19990901 in xemacs-21.2 */ +DEFUN ("hash-table-type", Fhash_table_type, 1, 1, 0, /* +Return the type of HASH-TABLE. +This can be one of `non-weak', `weak', `key-weak' or `value-weak'. +*/ + (hash_table)) +{ + switch (xhash_table (hash_table)->weakness) + { + case HASH_TABLE_WEAK: return Qweak; + case HASH_TABLE_KEY_WEAK: return Qkey_weak; + case HASH_TABLE_VALUE_WEAK: return Qvalue_weak; + default: return Qnon_weak; + } +} + /************************************************************************/ /* Mapping Functions */ /************************************************************************/ @@ -1156,21 +1208,20 @@ /* Complete the marking for semi-weak hash tables. */ int -finish_marking_weak_hash_tables (int (*obj_marked_p) (Lisp_Object), - void (*markobj) (Lisp_Object)) +finish_marking_weak_hash_tables (void) { Lisp_Object hash_table; int did_mark = 0; for (hash_table = Vall_weak_hash_tables; - !GC_NILP (hash_table); + !NILP (hash_table); hash_table = XHASH_TABLE (hash_table)->next_weak) { CONST Lisp_Hash_Table *ht = XHASH_TABLE (hash_table); CONST hentry *e = ht->hentries; CONST hentry *sentinel = e + ht->size; - if (! obj_marked_p (hash_table)) + if (! marked_p (hash_table)) /* The hash table is probably garbage. Ignore it. */ continue; @@ -1178,28 +1229,28 @@ half-marked, we may need to mark the other half if we're keeping this pair. */ #define MARK_OBJ(obj) \ -do { if (!obj_marked_p (obj)) markobj (obj), did_mark = 1; } while (0) +do { if (!marked_p (obj)) mark_object (obj), did_mark = 1; } while (0) - switch (ht->type) + switch (ht->weakness) { case HASH_TABLE_KEY_WEAK: for (; e < sentinel; e++) if (!HENTRY_CLEAR_P (e)) - if (obj_marked_p (e->key)) + if (marked_p (e->key)) MARK_OBJ (e->value); break; case HASH_TABLE_VALUE_WEAK: for (; e < sentinel; e++) if (!HENTRY_CLEAR_P (e)) - if (obj_marked_p (e->value)) + if (marked_p (e->value)) MARK_OBJ (e->key); break; case HASH_TABLE_KEY_CAR_WEAK: for (; e < sentinel; e++) if (!HENTRY_CLEAR_P (e)) - if (!CONSP (e->key) || obj_marked_p (XCAR (e->key))) + if (!CONSP (e->key) || marked_p (XCAR (e->key))) { MARK_OBJ (e->key); MARK_OBJ (e->value); @@ -1209,7 +1260,7 @@ case HASH_TABLE_VALUE_CAR_WEAK: for (; e < sentinel; e++) if (!HENTRY_CLEAR_P (e)) - if (!CONSP (e->value) || obj_marked_p (XCAR (e->value))) + if (!CONSP (e->value) || marked_p (XCAR (e->value))) { MARK_OBJ (e->key); MARK_OBJ (e->value); @@ -1225,17 +1276,17 @@ } void -prune_weak_hash_tables (int (*obj_marked_p) (Lisp_Object)) +prune_weak_hash_tables (void) { Lisp_Object hash_table, prev = Qnil; for (hash_table = Vall_weak_hash_tables; - !GC_NILP (hash_table); + !NILP (hash_table); hash_table = XHASH_TABLE (hash_table)->next_weak) { - if (! obj_marked_p (hash_table)) + if (! marked_p (hash_table)) { /* This hash table itself is garbage. Remove it from the list. */ - if (GC_NILP (prev)) + if (NILP (prev)) Vall_weak_hash_tables = XHASH_TABLE (hash_table)->next_weak; else XHASH_TABLE (prev)->next_weak = XHASH_TABLE (hash_table)->next_weak; @@ -1244,7 +1295,7 @@ { /* Now, scan over all the pairs. Remove all of the pairs in which the key or value, or both, is unmarked - (depending on the type of weak hash table). */ + (depending on the weakness of the hash table). */ Lisp_Hash_Table *ht = XHASH_TABLE (hash_table); hentry *entries = ht->hentries; hentry *sentinel = entries + ht->size; @@ -1254,7 +1305,7 @@ if (!HENTRY_CLEAR_P (e)) { again: - if (!obj_marked_p (e->key) || !obj_marked_p (e->value)) + if (!marked_p (e->key) || !marked_p (e->value)) { remhash_1 (ht, entries, e); if (!HENTRY_CLEAR_P (e)) @@ -1337,6 +1388,15 @@ return LISP_HASH (obj); } +DEFUN ("sxhash", Fsxhash, 1, 1, 0, /* +Return a hash value for OBJECT. +(equal obj1 obj2) implies (= (sxhash obj1) (sxhash obj2)). +*/ + (object)) +{ + return make_int (internal_hash (object, 0)); +} + #if 0 xxDEFUN ("internal-hash-value", Finternal_hash_value, 1, 1, 0, /* Hash value of OBJECT. For debugging. @@ -1367,11 +1427,13 @@ DEFSUBR (Fclrhash); DEFSUBR (Fmaphash); DEFSUBR (Fhash_table_count); + DEFSUBR (Fhash_table_test); DEFSUBR (Fhash_table_size); DEFSUBR (Fhash_table_rehash_size); DEFSUBR (Fhash_table_rehash_threshold); - DEFSUBR (Fhash_table_type); - DEFSUBR (Fhash_table_test); + DEFSUBR (Fhash_table_weakness); + DEFSUBR (Fhash_table_type); /* obsolete */ + DEFSUBR (Fsxhash); #if 0 DEFSUBR (Finternal_hash_value); #endif @@ -1379,18 +1441,22 @@ defsymbol (&Qhash_tablep, "hash-table-p"); defsymbol (&Qhash_table, "hash-table"); defsymbol (&Qhashtable, "hashtable"); - defsymbol (&Qweak, "weak"); - defsymbol (&Qkey_weak, "key-weak"); - defsymbol (&Qvalue_weak, "value-weak"); - defsymbol (&Qnon_weak, "non-weak"); + defsymbol (&Qweakness, "weakness"); + defsymbol (&Qvalue, "value"); defsymbol (&Qrehash_size, "rehash-size"); defsymbol (&Qrehash_threshold, "rehash-threshold"); - defkeyword (&Q_size, ":size"); + defsymbol (&Qweak, "weak"); /* obsolete */ + defsymbol (&Qkey_weak, "key-weak"); /* obsolete */ + defsymbol (&Qvalue_weak, "value-weak"); /* obsolete */ + defsymbol (&Qnon_weak, "non-weak"); /* obsolete */ + defkeyword (&Q_test, ":test"); - defkeyword (&Q_type, ":type"); + defkeyword (&Q_size, ":size"); defkeyword (&Q_rehash_size, ":rehash-size"); defkeyword (&Q_rehash_threshold, ":rehash-threshold"); + defkeyword (&Q_weakness, ":weakness"); + defkeyword (&Q_type, ":type"); /* obsolete */ } void @@ -1398,4 +1464,5 @@ { /* This must NOT be staticpro'd */ Vall_weak_hash_tables = Qnil; + pdump_wire_list (&Vall_weak_hash_tables); } diff -r 28d9c139be4c -r 11054d720c21 src/elhash.h --- a/src/elhash.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/elhash.h Mon Aug 13 11:26:11 2007 +0200 @@ -28,11 +28,10 @@ #define XHASH_TABLE(x) XRECORD (x, hash_table, struct Lisp_Hash_Table) #define XSETHASH_TABLE(x, p) XSETRECORD (x, p, hash_table) #define HASH_TABLEP(x) RECORDP (x, hash_table) -#define GC_HASH_TABLEP(x) GC_RECORDP (x, hash_table) #define CHECK_HASH_TABLE(x) CHECK_RECORD (x, hash_table) #define CONCHECK_HASH_TABLE(x) CONCHECK_RECORD (x, hash_table) -enum hash_table_type +enum hash_table_weakness { HASH_TABLE_NON_WEAK, HASH_TABLE_KEY_WEAK, @@ -49,6 +48,8 @@ HASH_TABLE_EQUAL }; +extern const struct lrecord_description hash_table_description[]; + EXFUN (Fcopy_hash_table, 1); EXFUN (Fhash_table_count, 1); EXFUN (Fgethash, 3); @@ -62,15 +63,16 @@ typedef int (*maphash_function_t) (Lisp_Object key, Lisp_Object value, void* extra_arg); +struct Lisp_Hash_Table; -Lisp_Object make_general_lisp_hash_table (size_t size, - enum hash_table_type type, - enum hash_table_test test, +Lisp_Object make_general_lisp_hash_table (enum hash_table_test test, + size_t size, + double rehash_size, double rehash_threshold, - double rehash_size); + enum hash_table_weakness weakness); Lisp_Object make_lisp_hash_table (size_t size, - enum hash_table_type type, + enum hash_table_weakness weakness, enum hash_table_test test); void elisp_maphash (maphash_function_t function, @@ -79,8 +81,9 @@ void elisp_map_remhash (maphash_function_t predicate, Lisp_Object hash_table, void *extra_arg); -int finish_marking_weak_hash_tables (int (*obj_marked_p) (Lisp_Object), - void (*markobj) (Lisp_Object)); -void prune_weak_hash_tables (int (*obj_marked_p) (Lisp_Object)); +int finish_marking_weak_hash_tables (void); +void prune_weak_hash_tables (void); + +void reorganize_hash_table (struct Lisp_Hash_Table *ht); #endif /* _XEMACS_ELHASH_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/emacs.c --- a/src/emacs.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/emacs.c Mon Aug 13 11:26:11 2007 +0200 @@ -151,7 +151,7 @@ Lisp_Object Vdoc_directory, Vconfigure_doc_directory; Lisp_Object Vconfigure_lock_directory; Lisp_Object Vdata_directory_list; -Lisp_Object Vinfo_directory, Vconfigure_info_directory; +Lisp_Object Vconfigure_info_directory; Lisp_Object Vsite_directory, Vconfigure_site_directory; Lisp_Object Vconfigure_info_path; Lisp_Object Vinternal_error_checking; @@ -221,8 +221,8 @@ int debug_paths; /* Save argv and argc. */ -char **initial_argv; -int initial_argc; +static char **initial_argv; +static int initial_argc; static void sort_args (int argc, char **argv); @@ -547,7 +547,8 @@ extern int malloc_cookie; #endif -#if !defined(SYSTEM_MALLOC) && !defined(HAVE_LIBMCHECK) +#if (!defined (SYSTEM_MALLOC) && !defined (HAVE_LIBMCHECK) \ + && !defined (DOUG_LEA_MALLOC)) /* Make sure that any libraries we link against haven't installed a hook for a gmalloc of a potentially incompatible version. */ /* If we're using libmcheck, the hooks have already been initialized, */ @@ -555,7 +556,7 @@ __malloc_hook = NULL; __realloc_hook = NULL; __free_hook = NULL; -#endif /* not SYSTEM_MALLOC */ +#endif /* not SYSTEM_MALLOC or HAVE_LIBMCHECK or DOUG_LEA_MALLOC */ noninteractive = 0; @@ -855,6 +856,10 @@ We try to do things in an order that minimizes the non-obvious dependencies between functions. */ +#ifdef PDUMP + initialized = restart || pdump_load (); +#endif + if (!initialized) { /* Initialize things so that new Lisp objects @@ -1253,7 +1258,7 @@ staticpro() Fprovide(symbol) intern() - pure_put() + Fput() xmalloc() defsymbol(), if it's absolutely necessary and you're sure that the symbol isn't referenced anywhere else in the initialization @@ -1266,7 +1271,6 @@ Any of the object-creating functions on alloc.c: e.g. make_pure_*() - Fpurecopy() make_string() build_string() make_vector() @@ -1276,7 +1280,6 @@ Fcons() listN() make_opaque_ptr() - make_opaque_long() perhaps a few others. */ @@ -1284,6 +1287,9 @@ /* Now allow Fprovide() statements to be made. */ init_provide_once (); + /* Do that before any specifier creation (esp. vars_of_glyphs()) */ + vars_of_specifier (); + vars_of_abbrev (); vars_of_alloc (); #ifdef HAVE_X_WINDOWS @@ -1393,7 +1399,6 @@ vars_of_search (); vars_of_select (); vars_of_sound (); - vars_of_specifier (); vars_of_symbols (); vars_of_syntax (); #ifdef HAVE_TOOLBARS @@ -1609,8 +1614,113 @@ garbage_collect_1 (); } #endif +#ifdef PDUMP + } else if (!restart) { + reinit_alloc_once_early (); + reinit_opaque_once_early (); + + reinit_console_type_create_stream (); +#ifdef HAVE_TTY + reinit_console_type_create_tty (); +#endif +#ifdef HAVE_X_WINDOWS + reinit_console_type_create_x (); + reinit_console_type_create_device_x (); +#endif +#ifdef HAVE_MS_WINDOWS + reinit_console_type_create_mswindows (); +#endif + + reinit_specifier_type_create (); + reinit_specifier_type_create_image (); + reinit_specifier_type_create_gutter (); + reinit_specifier_type_create_objects (); +#ifdef HAVE_TOOLBARS + reinit_specifier_type_create_toolbar (); +#endif + + structure_type_create (); + + structure_type_create_chartab (); + structure_type_create_faces (); + structure_type_create_rangetab (); + structure_type_create_hash_table (); + + lstream_type_create (); +#ifdef FILE_CODING + lstream_type_create_file_coding (); +#endif +#if defined (HAVE_MS_WINDOWS) && !defined(HAVE_MSG_SELECT) + lstream_type_create_mswindows_selectable (); +#endif +#ifdef HAVE_UNIX_PROCESSES + process_type_create_unix (); +#endif +#ifdef HAVE_WIN32_PROCESSES + process_type_create_nt (); +#endif + + reinit_vars_of_buffer (); + reinit_vars_of_console (); +#ifdef DEBUG_XEMACS + reinit_vars_of_debug (); +#endif + reinit_vars_of_device (); + reinit_vars_of_eval (); +#ifdef HAVE_X_WINDOWS + reinit_vars_of_event_Xt (); +#endif +#if defined(HAVE_TTY) && (defined (DEBUG_TTY_EVENT_STREAM) || !defined (HAVE_X_WINDOWS)) + reinit_vars_of_event_tty (); +#endif +#ifdef HAVE_MS_WINDOWS + reinit_vars_of_event_mswindows (); +#endif + reinit_vars_of_event_stream (); + reinit_vars_of_events (); + reinit_vars_of_extents (); + reinit_vars_of_font_lock (); + reinit_vars_of_glyphs (); + reinit_vars_of_glyphs_widget (); + reinit_vars_of_insdel (); + reinit_vars_of_lread (); + reinit_vars_of_lstream (); + reinit_vars_of_minibuf (); + reinit_vars_of_module (); + reinit_vars_of_objects (); + reinit_vars_of_print (); + reinit_vars_of_redisplay (); + reinit_vars_of_search (); + reinit_vars_of_scrollbar_x (); + reinit_vars_of_undo (); + reinit_vars_of_window (); + +#ifdef HAVE_MS_WINDOWS + reinit_vars_of_frame_mswindows (); +#endif + +#ifdef HAVE_X_WINDOWS + reinit_vars_of_device_x (); +#ifdef HAVE_MENUBARS + reinit_vars_of_menubar_x (); +#endif + reinit_vars_of_xselect (); +#if defined (HAVE_MENUBARS) || defined (HAVE_SCROLLBARS) || defined (HAVE_DIALOGS) || defined (HAVE_TOOLBARS) + reinit_vars_of_gui_x (); +#endif +#endif + +#if defined(MULE) && defined(HAVE_WNN) + reinit_vars_of_mule_wnn (); +#endif + + reinit_complex_vars_of_buffer (); + reinit_complex_vars_of_console (); + reinit_complex_vars_of_minibuf (); +#endif } + /* CONGRATULATIONS!!! We have successfully initialized the Lisp engine. */ @@ -2200,9 +2310,13 @@ { /* Disable all calls to free() when XEmacs is exiting and it doesn't */ /* matter. */ - __free_hook = voodoo_free_hook; + __free_hook = +#ifdef __GNUC__ /* prototype of __free_hook varies with glibc version */ + (__typeof__ (__free_hook)) +#endif + voodoo_free_hook; } -#endif +#endif /* GNU_MALLOC */ DEFUN ("kill-emacs", Fkill_emacs, 0, 1, "P", /* Exit the XEmacs job and kill it. Ask for confirmation, without argument. @@ -2256,13 +2370,17 @@ UNGCPRO; - shut_down_emacs (0, ((STRINGP (arg)) ? arg : Qnil)); + shut_down_emacs (0, STRINGP (arg) ? arg : Qnil); #if defined(GNU_MALLOC) - __free_hook = voodoo_free_hook; + __free_hook = +#ifdef __GNUC__ /* prototype of __free_hook varies with glibc version */ + (__typeof__ (__free_hook)) #endif - - exit ((INTP (arg)) ? XINT (arg) : 0); + voodoo_free_hook; +#endif + + exit (INTP (arg) ? XINT (arg) : 0); /* NOTREACHED */ return Qnil; /* I'm sick of the compiler warning */ } @@ -2344,11 +2462,11 @@ /* Now try to determine the actual path to the executable, to try to make the backtrace-determination process as foolproof as possible. */ - if (GC_STRINGP (Vinvocation_name)) + if (STRINGP (Vinvocation_name)) name = (char *) XSTRING_DATA (Vinvocation_name); else name = "xemacs"; - if (GC_STRINGP (Vinvocation_directory)) + if (STRINGP (Vinvocation_directory)) dir = (char *) XSTRING_DATA (Vinvocation_directory); if (!dir || dir[0] != '/') stderr_out ("`which %s`", name); @@ -2512,6 +2630,11 @@ symname_ext = 0; garbage_collect_1 (); + +#ifdef PDUMP + pdump (); +#else + #ifdef DOUG_LEA_MALLOC malloc_state_ptr = malloc_get_state (); #endif @@ -2525,6 +2648,7 @@ #ifdef DOUG_LEA_MALLOC free (malloc_state_ptr); #endif +#endif /* not PDUMP */ } #endif /* not MSDOS and EMX */ @@ -2784,7 +2908,7 @@ DEFVAR_LISP ("system-configuration", &Vsystem_configuration /* String naming the configuration XEmacs was built for. */ ); - Vsystem_configuration = Fpurecopy (build_string (EMACS_CONFIGURATION)); + Vsystem_configuration = build_string (EMACS_CONFIGURATION); #ifndef EMACS_CONFIG_OPTIONS # define EMACS_CONFIG_OPTIONS "UNKNOWN" @@ -2792,8 +2916,7 @@ DEFVAR_LISP ("system-configuration-options", &Vsystem_configuration_options /* String containing the configuration options XEmacs was built with. */ ); - Vsystem_configuration_options = Fpurecopy (build_string - (EMACS_CONFIG_OPTIONS)); + Vsystem_configuration_options = build_string (EMACS_CONFIG_OPTIONS); DEFVAR_LISP ("emacs-major-version", &Vemacs_major_version /* Major version number of this version of Emacs, as an integer. @@ -2859,7 +2982,7 @@ #ifndef XEMACS_CODENAME #define XEMACS_CODENAME "Noname" #endif - Vxemacs_codename = Fpurecopy (build_string (XEMACS_CODENAME)); + Vxemacs_codename = build_string (XEMACS_CODENAME); DEFVAR_BOOL ("noninteractive", &noninteractive1 /* Non-nil means XEmacs is running without interactive terminal. @@ -2933,7 +3056,6 @@ Vinternal_error_checking = Fcons (intern ("bufpos"), Vinternal_error_checking); #endif - Vinternal_error_checking = Fpurecopy (Vinternal_error_checking); DEFVAR_LISP ("path-separator", &Vpath_separator /* The directory separator in search paths, as a string. @@ -3160,7 +3282,7 @@ #endif } -#ifdef __sgi +#if defined(__sgi) && !defined(PDUMP) /* This is so tremendously ugly I'd puke. But then, it works. * The target is to override the static constructor from the * libiflPNG.so library which is maskerading as libz, and diff -r 28d9c139be4c -r 11054d720c21 src/emodules.c --- a/src/emodules.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/emodules.c Mon Aug 13 11:26:11 2007 +0200 @@ -215,7 +215,7 @@ if (modules == (emodules_list *)0) modules = (emodules_list *)xmalloc (sizeof(emodules_list)); modnum++; - modules = xrealloc (modules, modnum * sizeof(emodules_list)); + modules = (emodules_list *) xrealloc (modules, modnum * sizeof(emodules_list)); fs = modnum - 1; memset (&modules[fs], 0, sizeof(emodules_list)); @@ -526,8 +526,18 @@ } void +reinit_vars_of_module (void) +{ + emodules_depth = 0; + modules = (emodules_list *)0; + modnum = 0; +} + +void vars_of_module (void) { + reinit_vars_of_module (); + DEFVAR_LISP ("module-version", &Vmodule_version /* Emacs dynamic loading mechanism version, as a string. @@ -537,7 +547,7 @@ the dynamic loading technology used in Emacs, if required. It is not a given that this value will be the same as the Emacs version number. */ ); - Vmodule_version = Fpurecopy (build_string (EMODULES_VERSION)); + Vmodule_version = build_string (EMODULES_VERSION); DEFVAR_BOOL ("load-modules-quietly", &load_modules_quietly /* *Set to t if module loading is to be silent. @@ -575,9 +585,6 @@ staticpro (&Vmodule_extensions); load_modules_quietly = 0; - emodules_depth = 0; - modules = (emodules_list *)0; - modnum = 0; Vmodule_load_path = Qnil; Fprovide (intern ("modules")); } diff -r 28d9c139be4c -r 11054d720c21 src/eval.c --- a/src/eval.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/eval.c Mon Aug 13 11:26:11 2007 +0200 @@ -73,7 +73,7 @@ a SUBR with more than 8 arguments, use max_args == MANY. See the DEFUN macro in lisp.h) */ #define PRIMITIVE_FUNCALL(rv, fn, av, ac) do { \ - void (*PF_fn)() = (void (*)()) (fn); \ + void (*PF_fn)(void) = (void (*)(void)) fn; \ Lisp_Object *PF_av = (av); \ switch (ac) \ { \ @@ -170,7 +170,7 @@ int max_specpdl_size; /* Depth in Lisp evaluations and function calls. */ -int lisp_eval_depth; +static int lisp_eval_depth; /* Maximum allowed depth in Lisp evaluations and function calls. */ int max_lisp_eval_depth; @@ -295,9 +295,15 @@ write_c_string (trailer, printcharfun); } -DEFINE_LRECORD_IMPLEMENTATION ("subr", subr, - this_one_is_unmarkable, print_subr, 0, 0, 0, 0, - Lisp_Subr); +static const struct lrecord_description subr_description[] = { + { XD_DOC_STRING, offsetof(Lisp_Subr, doc) }, + { XD_END } +}; + +DEFINE_BASIC_LRECORD_IMPLEMENTATION ("subr", subr, + this_one_is_unmarkable, print_subr, 0, 0, 0, + subr_description, + Lisp_Subr); /************************************************************************/ /* Entering the debugger */ @@ -1004,8 +1010,6 @@ static Lisp_Object define_function (Lisp_Object name, Lisp_Object defn) { - if (purify_flag) - defn = Fpurecopy (defn); Ffset (name, defn); LOADHIST_ATTACH (name); return name; @@ -1078,14 +1082,7 @@ if (!NILP (args = XCDR (args))) { Lisp_Object doc = XCAR (args); -#if 0 /* FSFmacs */ - /* #### We should probably do this but it might be dangerous */ - if (purify_flag) - doc = Fpurecopy (doc); Fput (sym, Qvariable_documentation, doc); -#else - pure_put (sym, Qvariable_documentation, doc); -#endif if (!NILP (args = XCDR (args))) error ("too many arguments"); } @@ -1093,7 +1090,7 @@ #ifdef I18N3 if (!NILP (Vfile_domain)) - pure_put (sym, Qvariable_domain, Vfile_domain); + Fput (sym, Qvariable_domain, Vfile_domain); #endif LOADHIST_ATTACH (sym); @@ -1133,21 +1130,14 @@ if (!NILP (args = XCDR (args))) { Lisp_Object doc = XCAR (args); -#if 0 /* FSFmacs */ - /* #### We should probably do this but it might be dangerous */ - if (purify_flag) - doc = Fpurecopy (doc); Fput (sym, Qvariable_documentation, doc); -#else - pure_put (sym, Qvariable_documentation, doc); -#endif if (!NILP (args = XCDR (args))) error ("too many arguments"); } #ifdef I18N3 if (!NILP (Vfile_domain)) - pure_put (sym, Qvariable_domain, Vfile_domain); + Fput (sym, Qvariable_domain, Vfile_domain); #endif LOADHIST_ATTACH (sym); @@ -1167,7 +1157,7 @@ return ((INTP (documentation) && XINT (documentation) < 0) || - ((STRINGP (documentation)) && + (STRINGP (documentation) && (string_byte (XSTRING (documentation), 0) == '*')) || /* If (STRING . INTEGER), a negative integer means a user variable. */ @@ -2633,7 +2623,7 @@ { Fsignal (Qwrong_type_argument, Fcons (Qcommandp, - ((EQ (cmd, final)) + (EQ (cmd, final) ? list1 (cmd) : list2 (cmd, final)))); return Qnil; @@ -2750,12 +2740,11 @@ /* Attempt to avoid consing identical (string=) pure strings. */ file = Fsymbol_name (Fintern (file, Qnil)); } - - return Ffset (function, - Fpurecopy (Fcons (Qautoload, list4 (file, - docstring, - interactive, - type)))); + + return Ffset (function, Fcons (Qautoload, list4 (file, + docstring, + interactive, + type))); } Lisp_Object @@ -2955,7 +2944,7 @@ if (max_args == UNEVALLED) /* Optimize for the common case */ { backtrace.evalargs = 0; - val = (((Lisp_Object (*) (Lisp_Object)) (subr_function (subr))) + val = (((Lisp_Object (*) (Lisp_Object)) subr_function (subr)) (original_args)); } else if (nargs <= max_args) @@ -3009,7 +2998,7 @@ backtrace.args = args; backtrace.nargs = nargs; - val = (((Lisp_Object (*) (int, Lisp_Object *)) (subr_function (subr))) + val = (((Lisp_Object (*) (int, Lisp_Object *)) subr_function (subr)) (nargs, args)); UNGCPRO; @@ -3203,7 +3192,7 @@ } else if (max_args == MANY) { - val = ((Lisp_Object (*) (int, Lisp_Object *)) (subr_function (subr))) + val = ((Lisp_Object (*) (int, Lisp_Object *)) subr_function (subr)) (fun_nargs, fun_args); } else if (max_args == UNEVALLED) /* Can't funcall a special form */ @@ -3627,8 +3616,9 @@ } else { - struct gcpro gcpro1, gcpro2; - GCPRO2 (sym, val); + struct gcpro gcpro1, gcpro2, gcpro3; + Lisp_Object globals = Qnil; + GCPRO3 (sym, val, globals); for (; CONSP (val) && ((cond == RUN_HOOKS_TO_COMPLETION) @@ -3640,7 +3630,7 @@ { /* t indicates this hook has a local binding; it means to run the global binding too. */ - Lisp_Object globals = Fdefault_value (sym); + globals = Fdefault_value (sym); if ((! CONSP (globals) || EQ (XCAR (globals), Qlambda)) && ! NILP (globals)) @@ -4207,14 +4197,14 @@ /* gc_currently_forbidden = 1; Currently no reason to do this; */ cons = noseeum_cons (buffer, form); - opaque = (warning_string ? make_opaque_ptr (warning_string) : Qnil); + opaque = (warning_string ? make_opaque_ptr ((void *)warning_string) : Qnil); GCPRO2 (cons, opaque); /* Qerror not Qt, so you can get a backtrace */ tem = condition_case_1 (Qerror, catch_them_squirmers_eval_in_buffer, cons, caught_a_squirmer, opaque); free_cons (XCONS (cons)); - if (OPAQUEP (opaque)) + if (OPAQUE_PTRP (opaque)) free_opaque_ptr (opaque); UNGCPRO; @@ -4247,13 +4237,13 @@ speccount = specpdl_depth(); specbind (Qinhibit_quit, Qt); - opaque = (warning_string ? make_opaque_ptr (warning_string) : Qnil); + opaque = (warning_string ? make_opaque_ptr ((void *)warning_string) : Qnil); GCPRO1 (opaque); /* Qerror not Qt, so you can get a backtrace */ tem = condition_case_1 (Qerror, catch_them_squirmers_run_hook, hook_symbol, caught_a_squirmer, opaque); - if (OPAQUEP (opaque)) + if (OPAQUE_PTRP (opaque)) free_opaque_ptr (opaque); UNGCPRO; @@ -4283,7 +4273,7 @@ specbind (Qinhibit_quit, Qt); cons = noseeum_cons (hook_symbol, - warning_string ? make_opaque_ptr (warning_string) + warning_string ? make_opaque_ptr ((void *)warning_string) : Qnil); GCPRO1 (cons); /* Qerror not Qt, so you can get a backtrace */ @@ -4294,7 +4284,7 @@ allow_quit_safe_run_hook_caught_a_squirmer : safe_run_hook_caught_a_squirmer, cons); - if (OPAQUEP (XCDR (cons))) + if (OPAQUE_PTRP (XCDR (cons))) free_opaque_ptr (XCDR (cons)); free_cons (XCONS (cons)); UNGCPRO; @@ -4329,12 +4319,12 @@ specbind (Qinhibit_quit, Qt); /* gc_currently_forbidden = 1; Currently no reason to do this; */ - opaque = (warning_string ? make_opaque_ptr (warning_string) : Qnil); + opaque = (warning_string ? make_opaque_ptr ((void *)warning_string) : Qnil); /* Qerror not Qt, so you can get a backtrace */ tem = condition_case_1 (Qerror, catch_them_squirmers_call0, function, caught_a_squirmer, opaque); - if (OPAQUEP (opaque)) + if (OPAQUE_PTRP (opaque)) free_opaque_ptr (opaque); UNGCPRO; @@ -4379,12 +4369,12 @@ /* gc_currently_forbidden = 1; Currently no reason to do this; */ cons = noseeum_cons (function, object); - opaque = (warning_string ? make_opaque_ptr (warning_string) : Qnil); + opaque = (warning_string ? make_opaque_ptr ((void *)warning_string) : Qnil); /* Qerror not Qt, so you can get a backtrace */ tem = condition_case_1 (Qerror, catch_them_squirmers_call1, cons, caught_a_squirmer, opaque); - if (OPAQUEP (opaque)) + if (OPAQUE_PTRP (opaque)) free_opaque_ptr (opaque); free_cons (XCONS (cons)); UNGCPRO; @@ -4415,12 +4405,12 @@ /* gc_currently_forbidden = 1; Currently no reason to do this; */ cons = list3 (function, object1, object2); - opaque = (warning_string ? make_opaque_ptr (warning_string) : Qnil); + opaque = (warning_string ? make_opaque_ptr ((void *)warning_string) : Qnil); /* Qerror not Qt, so you can get a backtrace */ tem = condition_case_1 (Qerror, catch_them_squirmers_call2, cons, caught_a_squirmer, opaque); - if (OPAQUEP (opaque)) + if (OPAQUE_PTRP (opaque)) free_opaque_ptr (opaque); free_list (cons); UNGCPRO; @@ -5053,8 +5043,28 @@ } void +reinit_vars_of_eval (void) +{ + preparing_for_armageddon = 0; + in_warnings = 0; + Qunbound_suspended_errors_tag = make_opaque_ptr (&Qunbound_suspended_errors_tag); + staticpro_nodump (&Qunbound_suspended_errors_tag); + + specpdl_size = 50; + specpdl = xnew_array (struct specbinding, specpdl_size); + /* XEmacs change: increase these values. */ + max_specpdl_size = 3000; + max_lisp_eval_depth = 500; +#if 0 /* no longer used */ + throw_level = 0; +#endif +} + +void vars_of_eval (void) { + reinit_vars_of_eval (); + DEFVAR_INT ("max-specpdl-size", &max_specpdl_size /* Limit on number of Lisp variable bindings & unwind-protects before error. */ ); @@ -5156,13 +5166,10 @@ */ ); Vdebugger = Qnil; - preparing_for_armageddon = 0; - staticpro (&Vpending_warnings); Vpending_warnings = Qnil; - Vpending_warnings_tail = Qnil; /* no need to protect this */ - - in_warnings = 0; + pdump_wire (&Vpending_warnings_tail); + Vpending_warnings_tail = Qnil; staticpro (&Vautoload_queue); Vautoload_queue = Qnil; @@ -5175,18 +5182,5 @@ staticpro (&Vcurrent_error_state); Vcurrent_error_state = Qnil; /* errors as normal */ - Qunbound_suspended_errors_tag = make_opaque_long (0); - staticpro (&Qunbound_suspended_errors_tag); - - specpdl_size = 50; - specpdl_depth_counter = 0; - specpdl = xnew_array (struct specbinding, specpdl_size); - /* XEmacs change: increase these values. */ - max_specpdl_size = 3000; - max_lisp_eval_depth = 500; -#if 0 /* no longer used */ - throw_level = 0; -#endif - reinit_eval (); } diff -r 28d9c139be4c -r 11054d720c21 src/event-Xt.c --- a/src/event-Xt.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/event-Xt.c Mon Aug 13 11:26:11 2007 +0200 @@ -1569,8 +1569,13 @@ break; case Expose: - x_redraw_exposed_area (f, event->xexpose.x, event->xexpose.y, - event->xexpose.width, event->xexpose.height); + if (!check_for_ignored_expose (f, event->xexpose.x, event->xexpose.y, + event->xexpose.width, event->xexpose.height) + && + !find_matching_subwindow (f, event->xexpose.x, event->xexpose.y, + event->xexpose.width, event->xexpose.height)) + x_redraw_exposed_area (f, event->xexpose.x, event->xexpose.y, + event->xexpose.width, event->xexpose.height); break; case GraphicsExpose: /* This occurs when an XCopyArea's source area was @@ -1663,14 +1668,14 @@ /* Xt interval id's might not fit into an int (they're pointers, as it happens), so we need to provide a conversion list. */ -struct Xt_timeout +static struct Xt_timeout { int id; XtIntervalId interval_id; struct Xt_timeout *next; } *pending_timeouts, *completed_timeouts; -struct Xt_timeout_blocktype +static struct Xt_timeout_blocktype { Blocktype_declare (struct Xt_timeout); } *the_Xt_timeout_blocktype; @@ -2918,15 +2923,8 @@ } void -vars_of_event_Xt (void) +reinit_vars_of_event_Xt (void) { - dispatch_event_queue = Qnil; - staticpro (&dispatch_event_queue); - dispatch_event_queue_tail = Qnil; - - /* this function only makes safe calls */ - init_what_input_once (); - Xt_event_stream = xnew (struct event_stream); Xt_event_stream->event_pending_p = emacs_Xt_event_pending_p; Xt_event_stream->next_event_cb = emacs_Xt_next_event; @@ -2941,6 +2939,24 @@ Xt_event_stream->create_stream_pair_cb = emacs_Xt_create_stream_pair; Xt_event_stream->delete_stream_pair_cb = emacs_Xt_delete_stream_pair; + the_Xt_timeout_blocktype = Blocktype_new (struct Xt_timeout_blocktype); + + last_quit_check_signal_tick_count = 0; + + /* this function only makes safe calls */ + init_what_input_once (); +} + +void +vars_of_event_Xt (void) +{ + reinit_vars_of_event_Xt (); + + dispatch_event_queue = Qnil; + staticpro (&dispatch_event_queue); + dispatch_event_queue_tail = Qnil; + pdump_wire (&dispatch_event_queue_tail); + DEFVAR_BOOL ("modifier-keys-are-sticky", &modifier_keys_are_sticky /* *Non-nil makes modifier keys sticky. This means that you can release the modifier key before pressing down @@ -2966,10 +2982,6 @@ */ ); x_debug_events = 0; #endif - - the_Xt_timeout_blocktype = Blocktype_new (struct Xt_timeout_blocktype); - - last_quit_check_signal_tick_count = 0; } /* This mess is a hack that patches the shell widget to treat visual inheritance diff -r 28d9c139be4c -r 11054d720c21 src/event-msw.c --- a/src/event-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/event-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -98,7 +98,8 @@ static Lisp_Object mswindows_find_frame (HWND hwnd); static Lisp_Object mswindows_find_console (HWND hwnd); -static Lisp_Object mswindows_key_to_emacs_keysym(int mswindows_key, int mods); +static Lisp_Object mswindows_key_to_emacs_keysym (int mswindows_key, int mods, + int extendedp); static int mswindows_modifier_state (BYTE* keymap, int has_AltGr); static void mswindows_set_chord_timer (HWND hwnd); static int mswindows_button2_near_enough (POINTS p1, POINTS p2); @@ -144,6 +145,7 @@ /* These are Lisp integers; see DEFVARS in this file for description. */ int mswindows_dynamic_frame_resize; +int mswindows_meta_activates_menu; int mswindows_num_mouse_buttons; int mswindows_mouse_button_max_skew_x; int mswindows_mouse_button_max_skew_y; @@ -1659,15 +1661,17 @@ BYTE keymap[256]; int has_AltGr = mswindows_current_layout_has_AltGr (); int mods; + int extendedp = lParam & 0x1000000; Lisp_Object keysym; GetKeyboardState (keymap); mods = mswindows_modifier_state (keymap, has_AltGr); - /* Handle those keys for which TranslateMessage won't generate a WM_CHAR */ - if (!NILP (keysym = mswindows_key_to_emacs_keysym(wParam, mods))) + /* Handle non-printables */ + if (!NILP (keysym = mswindows_key_to_emacs_keysym (wParam, mods, + extendedp))) mswindows_enqueue_keypress_event (hwnd, keysym, mods); - else + else /* Normal keys & modifiers */ { int quit_ch = CONSOLE_QUIT_CHAR (XCONSOLE (mswindows_find_console (hwnd))); BYTE keymap_orig[256]; @@ -1685,9 +1689,9 @@ * to loosely track Left and Right modifiers on behalf of the OS, * without screwing up Windows NT which tracks them properly. */ if (wParam == VK_CONTROL) - keymap [(lParam & 0x1000000) ? VK_RCONTROL : VK_LCONTROL] |= 0x80; + keymap [extendedp ? VK_RCONTROL : VK_LCONTROL] |= 0x80; else if (wParam == VK_MENU) - keymap [(lParam & 0x1000000) ? VK_RMENU : VK_LMENU] |= 0x80; + keymap [extendedp ? VK_RMENU : VK_LMENU] |= 0x80; memcpy (keymap_orig, keymap, 256); @@ -1734,7 +1738,7 @@ } /* else */ } /* F10 causes menu activation by default. We do not want this */ - if (wParam != VK_F10) + if (wParam != VK_F10 && (mswindows_meta_activates_menu || wParam != VK_MENU)) goto defproc; break; @@ -1982,15 +1986,35 @@ case WM_PAINT: { - PAINTSTRUCT paintStruct; - - frame = XFRAME (mswindows_find_frame (hwnd)); - - BeginPaint (hwnd, &paintStruct); - mswindows_redraw_exposed_area (frame, - paintStruct.rcPaint.left, paintStruct.rcPaint.top, - paintStruct.rcPaint.right, paintStruct.rcPaint.bottom); - EndPaint (hwnd, &paintStruct); + /* According to the docs we need to check GetUpdateRect() before + actually doing a WM_PAINT */ + if (GetUpdateRect (hwnd, NULL, FALSE)) + { + PAINTSTRUCT paintStruct; + int x, y, width, height; + + frame = XFRAME (mswindows_find_frame (hwnd)); + + BeginPaint (hwnd, &paintStruct); + x = paintStruct.rcPaint.left; + y = paintStruct.rcPaint.top; + width = paintStruct.rcPaint.right - paintStruct.rcPaint.left; + height = paintStruct.rcPaint.bottom - paintStruct.rcPaint.top; + /* Normally we want to ignore expose events when child + windows are unmapped, however once we are in the guts of + WM_PAINT we need to make sure that we don't register + unmaps then because they will not actually occur. */ + if (!check_for_ignored_expose (frame, x, y, width, height)) + { + hold_ignored_expose_registration = 1; + mswindows_redraw_exposed_area (frame, x, y, width, height); + hold_ignored_expose_registration = 0; + } + + EndPaint (hwnd, &paintStruct); + } + else + goto defproc; } break; @@ -2142,6 +2166,23 @@ UNGCPRO; break; } + + case WM_MOUSEWHEEL: + { + int keys = LOWORD (wParam); /* Modifier key flags */ + int delta = (short) HIWORD (wParam); /* Wheel rotation amount */ + struct gcpro gcpro1, gcpro2; + + if (mswindows_handle_mousewheel_event (mswindows_find_frame (hwnd), keys, delta)) + { + GCPRO2 (emacs_event, fobj); + mswindows_pump_outstanding_events (); /* Can GC */ + UNGCPRO; + } + else + goto defproc; + break; + } #endif #ifdef HAVE_MENUBARS @@ -2417,67 +2458,100 @@ * Only returns non-Qnil for keys that don't generate WM_CHAR messages * or whose ASCII codes (like space) xemacs doesn't like. * Virtual key values are defined in winresrc.h - * XXX I'm not sure that KEYSYM("name") is the best thing to use here. */ -Lisp_Object mswindows_key_to_emacs_keysym(int mswindows_key, int mods) +Lisp_Object mswindows_key_to_emacs_keysym (int mswindows_key, int mods, + int extendedp) { - switch (mswindows_key) - { - /* First the predefined ones */ - case VK_BACK: return QKbackspace; - case VK_TAB: return QKtab; - case '\n': return QKlinefeed; /* No VK_LINEFEED in winresrc.h */ - case VK_RETURN: return QKreturn; - case VK_ESCAPE: return QKescape; - case VK_SPACE: return QKspace; - case VK_DELETE: return QKdelete; - - /* The rest */ - case VK_CLEAR: return KEYSYM ("clear"); /* Should do ^L ? */ - case VK_PRIOR: return KEYSYM ("prior"); - case VK_NEXT: return KEYSYM ("next"); - case VK_END: return KEYSYM ("end"); - case VK_HOME: return KEYSYM ("home"); - case VK_LEFT: return KEYSYM ("left"); - case VK_UP: return KEYSYM ("up"); - case VK_RIGHT: return KEYSYM ("right"); - case VK_DOWN: return KEYSYM ("down"); - case VK_SELECT: return KEYSYM ("select"); - case VK_PRINT: return KEYSYM ("print"); - case VK_EXECUTE: return KEYSYM ("execute"); - case VK_SNAPSHOT: return KEYSYM ("print"); - case VK_INSERT: return KEYSYM ("insert"); - case VK_HELP: return KEYSYM ("help"); -#if 0 /* XXX What are these supposed to do? */ - case VK_LWIN return KEYSYM (""); - case VK_RWIN return KEYSYM (""); + if (extendedp) /* Keys not present on a 82 key keyboard */ + { + switch (mswindows_key) + { + case VK_RETURN: return KEYSYM ("kp-enter"); + case VK_PRIOR: return KEYSYM ("prior"); + case VK_NEXT: return KEYSYM ("next"); + case VK_END: return KEYSYM ("end"); + case VK_HOME: return KEYSYM ("home"); + case VK_LEFT: return KEYSYM ("left"); + case VK_UP: return KEYSYM ("up"); + case VK_RIGHT: return KEYSYM ("right"); + case VK_DOWN: return KEYSYM ("down"); + case VK_INSERT: return KEYSYM ("insert"); + case VK_DELETE: return QKdelete; + } + } + else + { + switch (mswindows_key) + { + case VK_BACK: return QKbackspace; + case VK_TAB: return QKtab; + case '\n': return QKlinefeed; + case VK_CLEAR: return KEYSYM ("clear"); + case VK_RETURN: return QKreturn; + case VK_ESCAPE: return QKescape; + case VK_SPACE: return QKspace; + case VK_PRIOR: return KEYSYM ("kp-prior"); + case VK_NEXT: return KEYSYM ("kp-next"); + case VK_END: return KEYSYM ("kp-end"); + case VK_HOME: return KEYSYM ("kp-home"); + case VK_LEFT: return KEYSYM ("kp-left"); + case VK_UP: return KEYSYM ("kp-up"); + case VK_RIGHT: return KEYSYM ("kp-right"); + case VK_DOWN: return KEYSYM ("kp-down"); + case VK_SELECT: return KEYSYM ("select"); + case VK_PRINT: return KEYSYM ("print"); + case VK_EXECUTE: return KEYSYM ("execute"); + case VK_SNAPSHOT: return KEYSYM ("print"); + case VK_INSERT: return KEYSYM ("kp-insert"); + case VK_DELETE: return KEYSYM ("kp-delete"); + case VK_HELP: return KEYSYM ("help"); +#if 0 /* FSF Emacs allows these to return configurable syms/mods */ + case VK_LWIN return KEYSYM (""); + case VK_RWIN return KEYSYM (""); #endif - case VK_APPS: return KEYSYM ("menu"); - case VK_F1: return KEYSYM ("f1"); - case VK_F2: return KEYSYM ("f2"); - case VK_F3: return KEYSYM ("f3"); - case VK_F4: return KEYSYM ("f4"); - case VK_F5: return KEYSYM ("f5"); - case VK_F6: return KEYSYM ("f6"); - case VK_F7: return KEYSYM ("f7"); - case VK_F8: return KEYSYM ("f8"); - case VK_F9: return KEYSYM ("f9"); - case VK_F10: return KEYSYM ("f10"); - case VK_F11: return KEYSYM ("f11"); - case VK_F12: return KEYSYM ("f12"); - case VK_F13: return KEYSYM ("f13"); - case VK_F14: return KEYSYM ("f14"); - case VK_F15: return KEYSYM ("f15"); - case VK_F16: return KEYSYM ("f16"); - case VK_F17: return KEYSYM ("f17"); - case VK_F18: return KEYSYM ("f18"); - case VK_F19: return KEYSYM ("f19"); - case VK_F20: return KEYSYM ("f20"); - case VK_F21: return KEYSYM ("f21"); - case VK_F22: return KEYSYM ("f22"); - case VK_F23: return KEYSYM ("f23"); - case VK_F24: return KEYSYM ("f24"); - } + case VK_APPS: return KEYSYM ("menu"); + case VK_NUMPAD0: return KEYSYM ("kp-0"); + case VK_NUMPAD1: return KEYSYM ("kp-1"); + case VK_NUMPAD2: return KEYSYM ("kp-2"); + case VK_NUMPAD3: return KEYSYM ("kp-3"); + case VK_NUMPAD4: return KEYSYM ("kp-4"); + case VK_NUMPAD5: return KEYSYM ("kp-5"); + case VK_NUMPAD6: return KEYSYM ("kp-6"); + case VK_NUMPAD7: return KEYSYM ("kp-7"); + case VK_NUMPAD8: return KEYSYM ("kp-8"); + case VK_NUMPAD9: return KEYSYM ("kp-9"); + case VK_MULTIPLY: return KEYSYM ("kp-multiply"); + case VK_ADD: return KEYSYM ("kp-add"); + case VK_SEPARATOR: return KEYSYM ("kp-separator"); + case VK_SUBTRACT: return KEYSYM ("kp-subtract"); + case VK_DECIMAL: return KEYSYM ("kp-decimal"); + case VK_DIVIDE: return KEYSYM ("kp-divide"); + case VK_F1: return KEYSYM ("f1"); + case VK_F2: return KEYSYM ("f2"); + case VK_F3: return KEYSYM ("f3"); + case VK_F4: return KEYSYM ("f4"); + case VK_F5: return KEYSYM ("f5"); + case VK_F6: return KEYSYM ("f6"); + case VK_F7: return KEYSYM ("f7"); + case VK_F8: return KEYSYM ("f8"); + case VK_F9: return KEYSYM ("f9"); + case VK_F10: return KEYSYM ("f10"); + case VK_F11: return KEYSYM ("f11"); + case VK_F12: return KEYSYM ("f12"); + case VK_F13: return KEYSYM ("f13"); + case VK_F14: return KEYSYM ("f14"); + case VK_F15: return KEYSYM ("f15"); + case VK_F16: return KEYSYM ("f16"); + case VK_F17: return KEYSYM ("f17"); + case VK_F18: return KEYSYM ("f18"); + case VK_F19: return KEYSYM ("f19"); + case VK_F20: return KEYSYM ("f20"); + case VK_F21: return KEYSYM ("f21"); + case VK_F22: return KEYSYM ("f22"); + case VK_F23: return KEYSYM ("f23"); + case VK_F24: return KEYSYM ("f24"); + } + } return Qnil; } @@ -2877,20 +2951,10 @@ /************************************************************************/ /* initialization */ /************************************************************************/ - + void -vars_of_event_mswindows (void) +reinit_vars_of_event_mswindows (void) { - mswindows_u_dispatch_event_queue = Qnil; - staticpro (&mswindows_u_dispatch_event_queue); - mswindows_u_dispatch_event_queue_tail = Qnil; - - mswindows_s_dispatch_event_queue = Qnil; - staticpro (&mswindows_s_dispatch_event_queue); - mswindows_s_dispatch_event_queue_tail = Qnil; - - mswindows_error_caught_in_modal_loop = Qnil; - staticpro (&mswindows_error_caught_in_modal_loop); mswindows_in_modal_loop = 0; mswindows_pending_timers_count = 0; @@ -2917,6 +2981,31 @@ mswindows_event_stream->create_stream_pair_cb = emacs_mswindows_create_stream_pair; mswindows_event_stream->delete_stream_pair_cb = emacs_mswindows_delete_stream_pair; #endif +} + +void +vars_of_event_mswindows (void) +{ + reinit_vars_of_event_mswindows (); + + mswindows_u_dispatch_event_queue = Qnil; + staticpro (&mswindows_u_dispatch_event_queue); + mswindows_u_dispatch_event_queue_tail = Qnil; + pdump_wire (&mswindows_u_dispatch_event_queue_tail); + + mswindows_s_dispatch_event_queue = Qnil; + staticpro (&mswindows_s_dispatch_event_queue); + mswindows_s_dispatch_event_queue_tail = Qnil; + pdump_wire (&mswindows_u_dispatch_event_queue_tail); + + mswindows_error_caught_in_modal_loop = Qnil; + staticpro (&mswindows_error_caught_in_modal_loop); + + DEFVAR_BOOL ("mswindows-meta-activates-menu", &mswindows_meta_activates_menu /* +*Controls whether pressing and releasing the Meta (Alt) key should +activate the menubar. +Default is t. +*/ ); DEFVAR_BOOL ("mswindows-dynamic-frame-resize", &mswindows_dynamic_frame_resize /* *Controls redrawing frame contents during mouse-drag or keyboard resize @@ -2962,6 +3051,7 @@ mswindows_mouse_button_max_skew_x = 0; mswindows_mouse_button_max_skew_y = 0; mswindows_mouse_button_tolerance = 0; + mswindows_meta_activates_menu = 1; } void diff -r 28d9c139be4c -r 11054d720c21 src/event-stream.c --- a/src/event-stream.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/event-stream.c Mon Aug 13 11:26:11 2007 +0200 @@ -81,7 +81,6 @@ #include "keymap.h" #include "lstream.h" #include "macros.h" /* for defining_keyboard_macro */ -#include "opaque.h" #include "process.h" #include "window.h" @@ -102,8 +101,6 @@ Lisp_Object Qundefined_keystroke_sequence; -Lisp_Object Qcommand_execute; - Lisp_Object Qcommand_event_p; /* Hooks to run before and after each command. */ @@ -389,15 +386,15 @@ #define CHECK_COMMAND_BUILDER(x) CHECK_RECORD (x, command_builder) static Lisp_Object -mark_command_builder (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_command_builder (Lisp_Object obj) { struct command_builder *builder = XCOMMAND_BUILDER (obj); - markobj (builder->prefix_events); - markobj (builder->current_events); - markobj (builder->most_current_event); - markobj (builder->last_non_munged_event); - markobj (builder->munge_me[0].first_mungeable_event); - markobj (builder->munge_me[1].first_mungeable_event); + mark_object (builder->prefix_events); + mark_object (builder->current_events); + mark_object (builder->most_current_event); + mark_object (builder->last_non_munged_event); + mark_object (builder->munge_me[0].first_mungeable_event); + mark_object (builder->munge_me[1].first_mungeable_event); return builder->console; } @@ -985,7 +982,7 @@ used to indicate an absence of a timer. */ static int low_level_timeout_id_tick; -struct low_level_timeout_blocktype +static struct low_level_timeout_blocktype { Blocktype_declare (struct low_level_timeout); } *the_low_level_timeout_blocktype; @@ -1101,38 +1098,39 @@ static int timeout_id_tick; -/* Since timeout structures contain Lisp_Objects, they need to be GC'd - properly. The opaque data type provides a convenient way of doing - this without having to create a new Lisp object, since we can - provide our own mark function. */ - -struct timeout -{ - int id; /* Id we use to identify the timeout over its lifetime */ - int interval_id; /* Id for this particular interval; this may - be different each time the timeout is - signalled.*/ - Lisp_Object function, object; /* Function and object associated - with timeout. */ - EMACS_TIME next_signal_time; /* Absolute time when the timeout - is next going to be signalled. */ - unsigned int resignal_msecs; /* How far after the next timeout - should the one after that - occur? */ -}; - static Lisp_Object pending_timeout_list, pending_async_timeout_list; static Lisp_Object Vtimeout_free_list; static Lisp_Object -mark_timeout (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_timeout (Lisp_Object obj) { - struct timeout *tm = (struct timeout *) XOPAQUE_DATA (obj); - markobj (tm->function); + struct Lisp_Timeout *tm = XTIMEOUT (obj); + mark_object (tm->function); return tm->object; } +/* Should never, ever be called. (except by an external debugger) */ +static void +print_timeout (Lisp_Object obj, Lisp_Object printcharfun, int escapeflag) +{ + CONST struct Lisp_Timeout *t = XTIMEOUT (obj); + char buf[64]; + + sprintf (buf, "#", + (unsigned long) t); + write_c_string (buf, printcharfun); +} + +static const struct lrecord_description timeout_description[] = { + { XD_LISP_OBJECT, offsetof(struct Lisp_Timeout, function), 2 }, + { XD_END } +}; + +DEFINE_LRECORD_IMPLEMENTATION ("timeout", timeout, + mark_timeout, print_timeout, + 0, 0, 0, timeout_description, struct Lisp_Timeout); + /* Generate a timeout and return its ID. */ int @@ -1141,8 +1139,8 @@ Lisp_Object function, Lisp_Object object, int async_p) { - Lisp_Object op = allocate_managed_opaque (Vtimeout_free_list, 0); - struct timeout *timeout = (struct timeout *) XOPAQUE_DATA (op); + Lisp_Object op = allocate_managed_lcrecord (Vtimeout_free_list); + struct Lisp_Timeout *timeout = XTIMEOUT (op); EMACS_TIME current_time; EMACS_TIME interval; @@ -1191,7 +1189,7 @@ Lisp_Object *function, Lisp_Object *object) { Lisp_Object op = Qnil, rest; - struct timeout *timeout; + struct Lisp_Timeout *timeout; Lisp_Object *timeout_list; struct gcpro gcpro1; int id; @@ -1204,16 +1202,16 @@ /* Find the timeout on the list of pending ones. */ LIST_LOOP (rest, *timeout_list) { - timeout = (struct timeout *) XOPAQUE_DATA (XCAR (rest)); + timeout = XTIMEOUT (XCAR (rest)); if (timeout->interval_id == interval_id) break; } assert (!NILP (rest)); op = XCAR (rest); - timeout = (struct timeout *) XOPAQUE_DATA (op); + timeout = XTIMEOUT (op); /* We make sure to snarf the data out of the timeout object before - we free it with free_managed_opaque(). */ + we free it with free_managed_lcrecord(). */ id = timeout->id; *function = timeout->function; *object = timeout->object; @@ -1255,7 +1253,7 @@ *timeout_list = noseeum_cons (op, *timeout_list); } else - free_managed_opaque (Vtimeout_free_list, op); + free_managed_lcrecord (Vtimeout_free_list, op); UNGCPRO; return id; @@ -1264,7 +1262,7 @@ void event_stream_disable_wakeup (int id, int async_p) { - struct timeout *timeout = 0; + struct Lisp_Timeout *timeout = 0; Lisp_Object rest; Lisp_Object *timeout_list; @@ -1276,7 +1274,7 @@ /* Find the timeout on the list of pending ones, if it's still there. */ LIST_LOOP (rest, *timeout_list) { - timeout = (struct timeout *) XOPAQUE_DATA (XCAR (rest)); + timeout = XTIMEOUT (XCAR (rest)); if (timeout->id == id) break; } @@ -1292,14 +1290,14 @@ event_stream_remove_async_timeout (timeout->interval_id); else event_stream_remove_timeout (timeout->interval_id); - free_managed_opaque (Vtimeout_free_list, op); + free_managed_lcrecord (Vtimeout_free_list, op); } } static int event_stream_wakeup_pending_p (int id, int async_p) { - struct timeout *timeout; + struct Lisp_Timeout *timeout; Lisp_Object rest; Lisp_Object timeout_list; int found = 0; @@ -1313,7 +1311,7 @@ /* Find the element on the list of pending ones, if it's still there. */ LIST_LOOP (rest, timeout_list) { - timeout = (struct timeout *) XOPAQUE_DATA (XCAR (rest)); + timeout = XTIMEOUT (XCAR (rest)); if (timeout->id == id) { found = 1; @@ -4909,7 +4907,6 @@ deferror (&Qundefined_keystroke_sequence, "undefined-keystroke-sequence", "Undefined keystroke sequence", Qerror); - defsymbol (&Qcommand_execute, "command-execute"); DEFSUBR (Frecent_keys); DEFSUBR (Frecent_keys_ring_size); @@ -4966,22 +4963,36 @@ } void -vars_of_event_stream (void) +reinit_vars_of_event_stream (void) { recent_keys_ring_index = 0; recent_keys_ring_size = 100; + num_input_chars = 0; + Vtimeout_free_list = make_lcrecord_list (sizeof (struct Lisp_Timeout), + &lrecord_timeout); + staticpro_nodump (&Vtimeout_free_list); + the_low_level_timeout_blocktype = + Blocktype_new (struct low_level_timeout_blocktype); + something_happened = 0; + recursive_sit_for = Qnil; +} + +void +vars_of_event_stream (void) +{ + reinit_vars_of_event_stream (); Vrecent_keys_ring = Qnil; staticpro (&Vrecent_keys_ring); Vthis_command_keys = Qnil; staticpro (&Vthis_command_keys); Vthis_command_keys_tail = Qnil; - - num_input_chars = 0; + pdump_wire (&Vthis_command_keys_tail); command_event_queue = Qnil; staticpro (&command_event_queue); command_event_queue_tail = Qnil; + pdump_wire (&command_event_queue_tail); Vlast_selected_frame = Qnil; staticpro (&Vlast_selected_frame); @@ -4992,20 +5003,9 @@ pending_async_timeout_list = Qnil; staticpro (&pending_async_timeout_list); - Vtimeout_free_list = make_opaque_list (sizeof (struct timeout), - mark_timeout); - staticpro (&Vtimeout_free_list); - - the_low_level_timeout_blocktype = - Blocktype_new (struct low_level_timeout_blocktype); - - something_happened = 0; - last_point_position_buffer = Qnil; staticpro (&last_point_position_buffer); - recursive_sit_for = Qnil; - DEFVAR_LISP ("echo-keystrokes", &Vecho_keystrokes /* *Nonzero means echo unfinished commands after this many seconds of pause. */ ); diff -r 28d9c139be4c -r 11054d720c21 src/event-tty.c --- a/src/event-tty.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/event-tty.c Mon Aug 13 11:26:11 2007 +0200 @@ -245,7 +245,7 @@ /************************************************************************/ void -vars_of_event_tty (void) +reinit_vars_of_event_tty (void) { tty_event_stream = xnew (struct event_stream); @@ -264,6 +264,12 @@ } void +vars_of_event_tty (void) +{ + reinit_vars_of_event_tty (); +} + +void init_event_tty_late (void) { event_stream = tty_event_stream; diff -r 28d9c139be4c -r 11054d720c21 src/events.c --- a/src/events.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/events.c Mon Aug 13 11:26:11 2007 +0200 @@ -103,29 +103,29 @@ } static Lisp_Object -mark_event (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_event (Lisp_Object obj) { struct Lisp_Event *event = XEVENT (obj); switch (event->event_type) { case key_press_event: - markobj (event->event.key.keysym); + mark_object (event->event.key.keysym); break; case process_event: - markobj (event->event.process.process); + mark_object (event->event.process.process); break; case timeout_event: - markobj (event->event.timeout.function); - markobj (event->event.timeout.object); + mark_object (event->event.timeout.function); + mark_object (event->event.timeout.object); break; case eval_event: case misc_user_event: - markobj (event->event.eval.function); - markobj (event->event.eval.object); + mark_object (event->event.eval.function); + mark_object (event->event.eval.object); break; case magic_eval_event: - markobj (event->event.magic_eval.object); + mark_object (event->event.magic_eval.object); break; case button_press_event: case button_release_event: @@ -137,7 +137,7 @@ default: abort (); } - markobj (event->channel); + mark_object (event->channel); return event->next; } @@ -2229,11 +2229,28 @@ defsymbol (&Qbutton_release, "button-release"); defsymbol (&Qmisc_user, "misc-user"); defsymbol (&Qascii_character, "ascii-character"); + + defsymbol (&QKbackspace, "backspace"); + defsymbol (&QKtab, "tab"); + defsymbol (&QKlinefeed, "linefeed"); + defsymbol (&QKreturn, "return"); + defsymbol (&QKescape, "escape"); + defsymbol (&QKspace, "space"); + defsymbol (&QKdelete, "delete"); +} + + +void +reinit_vars_of_events (void) +{ + Vevent_resource = Qnil; } void vars_of_events (void) { + reinit_vars_of_events (); + DEFVAR_LISP ("character-set-property", &Vcharacter_set_property /* A symbol used to look up the 8-bit character of a keysym. To convert a keysym symbol to an 8-bit code, as when that key is @@ -2243,22 +2260,4 @@ variable. */ ); Vcharacter_set_property = Qnil; - - Vevent_resource = Qnil; - - QKbackspace = KEYSYM ("backspace"); - QKtab = KEYSYM ("tab"); - QKlinefeed = KEYSYM ("linefeed"); - QKreturn = KEYSYM ("return"); - QKescape = KEYSYM ("escape"); - QKspace = KEYSYM ("space"); - QKdelete = KEYSYM ("delete"); - - staticpro (&QKbackspace); - staticpro (&QKtab); - staticpro (&QKlinefeed); - staticpro (&QKreturn); - staticpro (&QKescape); - staticpro (&QKspace); - staticpro (&QKdelete); } diff -r 28d9c139be4c -r 11054d720c21 src/events.h --- a/src/events.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/events.h Mon Aug 13 11:26:11 2007 +0200 @@ -435,6 +435,29 @@ #endif }; +struct Lisp_Timeout +{ + struct lcrecord_header header; + int id; /* Id we use to identify the timeout over its lifetime */ + int interval_id; /* Id for this particular interval; this may + be different each time the timeout is + signalled.*/ + Lisp_Object function, object; /* Function and object associated + with timeout. */ + EMACS_TIME next_signal_time; /* Absolute time when the timeout + is next going to be signalled. */ + unsigned int resignal_msecs; /* How far after the next timeout + should the one after that + occur? */ +}; + +DECLARE_LRECORD (timeout, struct Lisp_Timeout); +#define XTIMEOUT(x) XRECORD (x, timeout, struct Lisp_Timeout) +#define XSETTIMEOUT(x, p) XSETRECORD (x, p, timeout) +#define TIMEOUTP(x) RECORDP (x, timeout) +#define CHECK_TIMEOUT(x) CHECK_RECORD (x, timeout) +#define CONCHECK_TIMEOUT(x) CONCHECK_RECORD (x, timeout) + struct Lisp_Event { /* header->next (aka XEVENT_NEXT ()) is used as follows: @@ -466,7 +489,6 @@ #define XEVENT(x) XRECORD (x, event, struct Lisp_Event) #define XSETEVENT(x, p) XSETRECORD (x, p, event) #define EVENTP(x) RECORDP (x, event) -#define GC_EVENTP(x) GC_RECORDP (x, event) #define CHECK_EVENT(x) CHECK_RECORD (x, event) #define CONCHECK_EVENT(x) CONCHECK_RECORD (x, event) diff -r 28d9c139be4c -r 11054d720c21 src/extents.c --- a/src/extents.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/extents.c Mon Aug 13 11:26:11 2007 +0200 @@ -260,7 +260,7 @@ Gap_Array_Marker *markers; } Gap_Array; -Gap_Array_Marker *gap_array_marker_freelist; +static Gap_Array_Marker *gap_array_marker_freelist; /* Convert a "memory position" (i.e. taking the gap into account) into the address of the element at (i.e. after) that position. "Memory @@ -301,7 +301,7 @@ Extent_List_Marker *markers; } Extent_List; -Extent_List_Marker *extent_list_marker_freelist; +static Extent_List_Marker *extent_list_marker_freelist; #define EXTENT_LESS_VALS(e,st,nd) ((extent_start (e) < (st)) || \ ((extent_start (e) == (st)) && \ @@ -444,9 +444,6 @@ Lisp_Object Qwhitespace; /* Qtext defined in general.c */ -/* partially used in redisplay */ -Lisp_Object Qglyph_invisible; - Lisp_Object Qcopy_function; Lisp_Object Qpaste_function; @@ -910,18 +907,18 @@ /************************************************************************/ static Lisp_Object -mark_extent_auxiliary (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_extent_auxiliary (Lisp_Object obj) { struct extent_auxiliary *data = XEXTENT_AUXILIARY (obj); - markobj (data->begin_glyph); - markobj (data->end_glyph); - markobj (data->invisible); - markobj (data->children); - markobj (data->read_only); - markobj (data->mouse_face); - markobj (data->initial_redisplay_function); - markobj (data->before_change_functions); - markobj (data->after_change_functions); + mark_object (data->begin_glyph); + mark_object (data->end_glyph); + mark_object (data->invisible); + mark_object (data->children); + mark_object (data->read_only); + mark_object (data->mouse_face); + mark_object (data->initial_redisplay_function); + mark_object (data->before_change_functions); + mark_object (data->after_change_functions); return data->parent; } @@ -973,7 +970,7 @@ static void soe_invalidate (Lisp_Object obj); static Lisp_Object -mark_extent_info (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_extent_info (Lisp_Object obj) { struct extent_info *data = (struct extent_info *) XEXTENT_INFO (obj); int i; @@ -996,7 +993,7 @@ Lisp_Object exobj; XSETEXTENT (exobj, extent); - markobj (exobj); + mark_object (exobj); } } @@ -2913,7 +2910,7 @@ extent objects. They are similar to the functions for other lrecord objects. allocate_extent() is in alloc.c, not here. */ -static Lisp_Object mark_extent (Lisp_Object, void (*) (Lisp_Object)); +static Lisp_Object mark_extent (Lisp_Object); static int extent_equal (Lisp_Object, Lisp_Object, int depth); static unsigned long extent_hash (Lisp_Object obj, int depth); static void print_extent (Lisp_Object obj, Lisp_Object printcharfun, @@ -2945,12 +2942,12 @@ struct extent); static Lisp_Object -mark_extent (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_extent (Lisp_Object obj) { struct extent *extent = XEXTENT (obj); - markobj (extent_object (extent)); - markobj (extent_no_chase_normal_field (extent, face)); + mark_object (extent_object (extent)); + mark_object (extent_no_chase_normal_field (extent, face)); return extent->plist; } @@ -2969,11 +2966,9 @@ if (extent_detached_p (ext)) strcpy (bp, "detached"); else - { - Bufpos from = XINT (Fextent_start_position (obj)); - Bufpos to = XINT (Fextent_end_position (obj)); - sprintf (bp, "%d, %d", from, to); - } + sprintf (bp, "%ld, %ld", + (long) XINT (Fextent_start_position (obj)), + (long) XINT (Fextent_end_position (obj))); bp += strlen (bp); *bp++ = (extent_end_open_p (anc) ? ')': ']'); if (!NILP (extent_end_glyph (anc))) *bp++ = '*'; @@ -3184,7 +3179,7 @@ return -1; } - return external_remprop (&ext->plist, prop, 0, ERROR_ME); + return external_remprop (extent_plist_addr (ext), prop, 0, ERROR_ME); } static Lisp_Object @@ -6722,8 +6717,6 @@ defsymbol (&Qwhitespace, "whitespace"); /* Qtext defined in general.c */ - defsymbol (&Qglyph_invisible, "glyph-invisible"); - defsymbol (&Qpaste_function, "paste-function"); defsymbol (&Qcopy_function, "copy-function"); @@ -6800,8 +6793,26 @@ } void +reinit_vars_of_extents (void) +{ + extent_auxiliary_defaults.begin_glyph = Qnil; + extent_auxiliary_defaults.end_glyph = Qnil; + extent_auxiliary_defaults.parent = Qnil; + extent_auxiliary_defaults.children = Qnil; + extent_auxiliary_defaults.priority = 0; + extent_auxiliary_defaults.invisible = Qnil; + extent_auxiliary_defaults.read_only = Qnil; + extent_auxiliary_defaults.mouse_face = Qnil; + extent_auxiliary_defaults.initial_redisplay_function = Qnil; + extent_auxiliary_defaults.before_change_functions = Qnil; + extent_auxiliary_defaults.after_change_functions = Qnil; +} + +void vars_of_extents (void) { + reinit_vars_of_extents (); + DEFVAR_INT ("mouse-highlight-priority", &mouse_highlight_priority /* The priority to use for the mouse-highlighting pseudo-extent that is used to highlight extents with the `mouse-face' attribute set. @@ -6828,18 +6839,6 @@ Vextent_face_reusable_list = Fcons (Qnil, Qnil); staticpro (&Vextent_face_reusable_list); - - extent_auxiliary_defaults.begin_glyph = Qnil; - extent_auxiliary_defaults.end_glyph = Qnil; - extent_auxiliary_defaults.parent = Qnil; - extent_auxiliary_defaults.children = Qnil; - extent_auxiliary_defaults.priority = 0; - extent_auxiliary_defaults.invisible = Qnil; - extent_auxiliary_defaults.read_only = Qnil; - extent_auxiliary_defaults.mouse_face = Qnil; - extent_auxiliary_defaults.initial_redisplay_function = Qnil; - extent_auxiliary_defaults.before_change_functions = Qnil; - extent_auxiliary_defaults.after_change_functions = Qnil; } void diff -r 28d9c139be4c -r 11054d720c21 src/extents.h --- a/src/extents.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/extents.h Mon Aug 13 11:26:11 2007 +0200 @@ -27,7 +27,6 @@ #define XEXTENT(x) XRECORD (x, extent, struct extent) #define XSETEXTENT(x, p) XSETRECORD (x, p, extent) #define EXTENTP(x) RECORDP (x, extent) -#define GC_EXTENTP(x) GC_RECORDP (x, extent) #define CHECK_EXTENT(x) CHECK_RECORD (x, extent) #define CONCHECK_EXTENT(x) CONCHECK_RECORD (x, extent) @@ -147,7 +146,6 @@ XRECORD (x, extent_auxiliary, struct extent_auxiliary) #define XSETEXTENT_AUXILIARY(x, p) XSETRECORD (x, p, extent_auxiliary) #define EXTENT_AUXILIARYP(x) RECORDP (x, extent_auxiliary) -#define GC_EXTENT_AUXILIARYP(x) GC_RECORDP (x, extent_auxiliary) #define CHECK_EXTENT_AUXILIARY(x) CHECK_RECORD (x, extent_auxiliary) #define CONCHECK_EXTENT_AUXILIARY(x) CONCHECK_RECORD (x, extent_auxiliary) @@ -163,7 +161,6 @@ #define XEXTENT_INFO(x) XRECORD (x, extent_info, struct extent_info) #define XSETEXTENT_INFO(x, p) XSETRECORD (x, p, extent_info) #define EXTENT_INFOP(x) RECORDP (x, extent_info) -#define GC_EXTENT_INFOP(x) GC_RECORDP (x, extent_info) #define CHECK_EXTENT_INFO(x) CHECK_RECORD (x, extent_info) #define CONCHECK_EXTENT_INFO(x) CONCHECK_RECORD (x, extent_info) diff -r 28d9c139be4c -r 11054d720c21 src/faces.c --- a/src/faces.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/faces.c Mon Aug 13 11:26:11 2007 +0200 @@ -73,26 +73,26 @@ static Lisp_Object -mark_face (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_face (Lisp_Object obj) { struct Lisp_Face *face = XFACE (obj); - markobj (face->name); - markobj (face->doc_string); + mark_object (face->name); + mark_object (face->doc_string); - markobj (face->foreground); - markobj (face->background); - markobj (face->font); - markobj (face->display_table); - markobj (face->background_pixmap); - markobj (face->underline); - markobj (face->strikethru); - markobj (face->highlight); - markobj (face->dim); - markobj (face->blinking); - markobj (face->reverse); + mark_object (face->foreground); + mark_object (face->background); + mark_object (face->font); + mark_object (face->display_table); + mark_object (face->background_pixmap); + mark_object (face->underline); + mark_object (face->strikethru); + mark_object (face->highlight); + mark_object (face->dim); + mark_object (face->blinking); + mark_object (face->reverse); - markobj (face->charsets_warned_about); + mark_object (face->charsets_warned_about); return face->plist; } @@ -171,18 +171,18 @@ struct Lisp_Face *f = XFACE (obj); return - ((EQ (prop, Qforeground)) ? f->foreground : - (EQ (prop, Qbackground)) ? f->background : - (EQ (prop, Qfont)) ? f->font : - (EQ (prop, Qdisplay_table)) ? f->display_table : - (EQ (prop, Qbackground_pixmap)) ? f->background_pixmap : - (EQ (prop, Qunderline)) ? f->underline : - (EQ (prop, Qstrikethru)) ? f->strikethru : - (EQ (prop, Qhighlight)) ? f->highlight : - (EQ (prop, Qdim)) ? f->dim : - (EQ (prop, Qblinking)) ? f->blinking : - (EQ (prop, Qreverse)) ? f->reverse : - (EQ (prop, Qdoc_string)) ? f->doc_string : + (EQ (prop, Qforeground) ? f->foreground : + EQ (prop, Qbackground) ? f->background : + EQ (prop, Qfont) ? f->font : + EQ (prop, Qdisplay_table) ? f->display_table : + EQ (prop, Qbackground_pixmap) ? f->background_pixmap : + EQ (prop, Qunderline) ? f->underline : + EQ (prop, Qstrikethru) ? f->strikethru : + EQ (prop, Qhighlight) ? f->highlight : + EQ (prop, Qdim) ? f->dim : + EQ (prop, Qblinking) ? f->blinking : + EQ (prop, Qreverse) ? f->reverse : + EQ (prop, Qdoc_string) ? f->doc_string : external_plist_get (&f->plist, prop, 0, ERROR_ME)); } @@ -264,9 +264,15 @@ return result; } +static const struct lrecord_description face_description[] = { + { XD_LISP_OBJECT, offsetof(struct Lisp_Face, name), 2 }, + { XD_LISP_OBJECT, offsetof(struct Lisp_Face, foreground), 13 }, + { XD_END } +}; + DEFINE_LRECORD_IMPLEMENTATION_WITH_PROPS ("face", face, mark_face, print_face, 0, face_equal, - face_hash, 0, face_getprop, + face_hash, face_description, face_getprop, face_putprop, face_remprop, face_plist, struct Lisp_Face); @@ -981,8 +987,7 @@ /* mark for GC a dynarr of face cachels. */ void -mark_face_cachels (face_cachel_dynarr *elements, - void (*markobj) (Lisp_Object)) +mark_face_cachels (face_cachel_dynarr *elements) { int elt; @@ -998,13 +1003,13 @@ for (i = 0; i < NUM_LEADING_BYTES; i++) if (!NILP (cachel->font[i]) && !UNBOUNDP (cachel->font[i])) - markobj (cachel->font[i]); + mark_object (cachel->font[i]); } - markobj (cachel->face); - markobj (cachel->foreground); - markobj (cachel->background); - markobj (cachel->display_table); - markobj (cachel->background_pixmap); + mark_object (cachel->face); + mark_object (cachel->foreground); + mark_object (cachel->background); + mark_object (cachel->display_table); + mark_object (cachel->background_pixmap); } } diff -r 28d9c139be4c -r 11054d720c21 src/faces.h --- a/src/faces.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/faces.h Mon Aug 13 11:26:11 2007 +0200 @@ -226,7 +226,6 @@ #define XFACE(x) XRECORD (x, face, struct Lisp_Face) #define XSETFACE(x, p) XSETRECORD (x, p, face) #define FACEP(x) RECORDP (x, face) -#define GC_FACEP(x) GC_RECORDP (x, face) #define CHECK_FACE(x) CHECK_RECORD (x, face) Lisp_Object ensure_face_cachel_contains_charset (struct face_cachel *cachel, @@ -241,8 +240,7 @@ void face_cachel_charset_font_metric_info (struct face_cachel *cachel, unsigned char *charsets, struct font_metric_info *fm); -void mark_face_cachels (face_cachel_dynarr *elements, - void (*markobj) (Lisp_Object)); +void mark_face_cachels (face_cachel_dynarr *elements); void mark_face_cachels_as_clean (struct window *w); void mark_face_cachels_as_not_updated (struct window *w); void reset_face_cachel (struct face_cachel *inst); diff -r 28d9c139be4c -r 11054d720c21 src/file-coding.c --- a/src/file-coding.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/file-coding.c Mon Aug 13 11:26:11 2007 +0200 @@ -36,7 +36,7 @@ #endif #include "file-coding.h" -Lisp_Object Qbuffer_file_coding_system, Qcoding_system_error; +Lisp_Object Qcoding_system_error; Lisp_Object Vkeyboard_coding_system; Lisp_Object Vterminal_coding_system; @@ -47,14 +47,33 @@ /* Table of symbols identifying each coding category. */ Lisp_Object coding_category_symbol[CODING_CATEGORY_LAST + 1]; -/* Coding system currently associated with each coding category. */ -Lisp_Object coding_category_system[CODING_CATEGORY_LAST + 1]; - -/* Table of all coding categories in decreasing order of priority. - This describes a permutation of the possible coding categories. */ -int coding_category_by_priority[CODING_CATEGORY_LAST + 1]; - -Lisp_Object Qcoding_system_p; + + +struct file_coding_dump { + /* Coding system currently associated with each coding category. */ + Lisp_Object coding_category_system[CODING_CATEGORY_LAST + 1]; + + /* Table of all coding categories in decreasing order of priority. + This describes a permutation of the possible coding categories. */ + int coding_category_by_priority[CODING_CATEGORY_LAST + 1]; + + Lisp_Object ucs_to_mule_table[65536]; +} *fcd; + +static const struct lrecord_description fcd_description_1[] = { + { XD_LISP_OBJECT, offsetof(struct file_coding_dump, coding_category_system), CODING_CATEGORY_LAST + 1 }, + { XD_LISP_OBJECT, offsetof(struct file_coding_dump, ucs_to_mule_table), 65536 }, + { XD_END } +}; + +static const struct struct_description fcd_description = { + sizeof(struct file_coding_dump), + fcd_description_1 +}; + +Lisp_Object mule_to_ucs_table; + +Lisp_Object Qcoding_systemp; Lisp_Object Qraw_text, Qno_conversion, Qccl, Qiso2022; /* Qinternal in general.c */ @@ -227,6 +246,26 @@ Dynarr_declare (codesys_prop); } codesys_prop_dynarr; +static const struct lrecord_description codesys_prop_description_1[] = { + { XD_LISP_OBJECT, offsetof(codesys_prop, sym), 1 }, + { XD_END } +}; + +static const struct struct_description codesys_prop_description = { + sizeof(codesys_prop), + codesys_prop_description_1 +}; + +static const struct lrecord_description codesys_prop_dynarr_description_1[] = { + XD_DYNARR_DESC(codesys_prop_dynarr, &codesys_prop_description), + { XD_END } +}; + +static const struct struct_description codesys_prop_dynarr_description = { + sizeof(codesys_prop_dynarr), + codesys_prop_dynarr_description_1 +}; + codesys_prop_dynarr *the_codesys_prop_dynarr; enum codesys_prop_enum @@ -241,7 +280,7 @@ /* Coding system functions */ /************************************************************************/ -static Lisp_Object mark_coding_system (Lisp_Object, void (*) (Lisp_Object)); +static Lisp_Object mark_coding_system (Lisp_Object); static void print_coding_system (Lisp_Object, Lisp_Object, int); static void finalize_coding_system (void *header, int for_disksave); @@ -287,16 +326,16 @@ struct Lisp_Coding_System); static Lisp_Object -mark_coding_system (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_coding_system (Lisp_Object obj) { Lisp_Coding_System *codesys = XCODING_SYSTEM (obj); - markobj (CODING_SYSTEM_NAME (codesys)); - markobj (CODING_SYSTEM_DOC_STRING (codesys)); - markobj (CODING_SYSTEM_MNEMONIC (codesys)); - markobj (CODING_SYSTEM_EOL_LF (codesys)); - markobj (CODING_SYSTEM_EOL_CRLF (codesys)); - markobj (CODING_SYSTEM_EOL_CR (codesys)); + mark_object (CODING_SYSTEM_NAME (codesys)); + mark_object (CODING_SYSTEM_DOC_STRING (codesys)); + mark_object (CODING_SYSTEM_MNEMONIC (codesys)); + mark_object (CODING_SYSTEM_EOL_LF (codesys)); + mark_object (CODING_SYSTEM_EOL_CRLF (codesys)); + mark_object (CODING_SYSTEM_EOL_CR (codesys)); switch (CODING_SYSTEM_TYPE (codesys)) { @@ -304,15 +343,15 @@ int i; case CODESYS_ISO2022: for (i = 0; i < 4; i++) - markobj (CODING_SYSTEM_ISO2022_INITIAL_CHARSET (codesys, i)); + mark_object (CODING_SYSTEM_ISO2022_INITIAL_CHARSET (codesys, i)); if (codesys->iso2022.input_conv) { for (i = 0; i < Dynarr_length (codesys->iso2022.input_conv); i++) { struct charset_conversion_spec *ccs = Dynarr_atp (codesys->iso2022.input_conv, i); - markobj (ccs->from_charset); - markobj (ccs->to_charset); + mark_object (ccs->from_charset); + mark_object (ccs->to_charset); } } if (codesys->iso2022.output_conv) @@ -321,22 +360,22 @@ { struct charset_conversion_spec *ccs = Dynarr_atp (codesys->iso2022.output_conv, i); - markobj (ccs->from_charset); - markobj (ccs->to_charset); + mark_object (ccs->from_charset); + mark_object (ccs->to_charset); } } break; case CODESYS_CCL: - markobj (CODING_SYSTEM_CCL_DECODE (codesys)); - markobj (CODING_SYSTEM_CCL_ENCODE (codesys)); + mark_object (CODING_SYSTEM_CCL_DECODE (codesys)); + mark_object (CODING_SYSTEM_CCL_ENCODE (codesys)); break; #endif /* MULE */ default: break; } - markobj (CODING_SYSTEM_PRE_WRITE_CONVERSION (codesys)); + mark_object (CODING_SYSTEM_PRE_WRITE_CONVERSION (codesys)); return CODING_SYSTEM_POST_READ_CONVERSION (codesys); } @@ -1301,7 +1340,7 @@ order. */ for (j = 0; j <= CODING_CATEGORY_LAST; j++) { - int cat = coding_category_by_priority[j]; + int cat = fcd->coding_category_by_priority[j]; if (category_to_priority[cat] < 0) category_to_priority[cat] = i++; } @@ -1310,7 +1349,7 @@ constructed. */ for (i = 0; i <= CODING_CATEGORY_LAST; i++) - coding_category_by_priority[category_to_priority[i]] = i; + fcd->coding_category_by_priority[category_to_priority[i]] = i; /* Phew! That was confusing. */ return Qnil; @@ -1325,7 +1364,7 @@ Lisp_Object list = Qnil; for (i = CODING_CATEGORY_LAST; i >= 0; i--) - list = Fcons (coding_category_symbol[coding_category_by_priority[i]], + list = Fcons (coding_category_symbol[fcd->coding_category_by_priority[i]], list); return list; } @@ -1338,7 +1377,7 @@ int cat = decode_coding_category (coding_category); coding_system = Fget_coding_system (coding_system); - coding_category_system[cat] = coding_system; + fcd->coding_category_system[cat] = coding_system; return Qnil; } @@ -1348,7 +1387,7 @@ (coding_category)) { int cat = decode_coding_category (coding_category); - Lisp_Object sys = coding_category_system[cat]; + Lisp_Object sys = fcd->coding_category_system[cat]; if (!NILP (sys)) return XCODING_SYSTEM_NAME (sys); @@ -1582,13 +1621,13 @@ the first one that is allowed. */ for (i = 0; i <= CODING_CATEGORY_LAST; i++) { - cat = coding_category_by_priority[i]; + cat = fcd->coding_category_by_priority[i]; if ((mask & (1 << cat)) && - !NILP (coding_category_system[cat])) + !NILP (fcd->coding_category_system[cat])) break; } if (cat >= 0) - return coding_category_system[cat]; + return fcd->coding_category_system[cat]; else return Fget_coding_system (Qraw_text); } @@ -1620,26 +1659,65 @@ if (XCODING_SYSTEM_TYPE (*codesys_in_out) == CODESYS_AUTODETECT || *eol_type_in_out == EOL_AUTODETECT) { - - while (1) + unsigned char random_buffer[4096]; + int nread; + Lisp_Object coding_system = Qnil; + + nread = Lstream_read (stream, random_buffer, sizeof (random_buffer)); + if (nread) { - unsigned char random_buffer[4096]; - int nread; - - nread = Lstream_read (stream, random_buffer, sizeof (random_buffer)); - if (!nread) - break; - if (detect_coding_type (&decst, random_buffer, nread, - XCODING_SYSTEM_TYPE (*codesys_in_out) != - CODESYS_AUTODETECT)) - break; + unsigned char *cp = random_buffer; + + while (cp < random_buffer + nread) + { + if ((*cp++ == 'c') && (cp < random_buffer + nread) && + (*cp++ == 'o') && (cp < random_buffer + nread) && + (*cp++ == 'd') && (cp < random_buffer + nread) && + (*cp++ == 'i') && (cp < random_buffer + nread) && + (*cp++ == 'n') && (cp < random_buffer + nread) && + (*cp++ == 'g') && (cp < random_buffer + nread) && + (*cp++ == ':') && (cp < random_buffer + nread)) + { + unsigned char coding_system_name[4096 - 6]; + unsigned char *np = coding_system_name; + + while ( (cp < random_buffer + nread) + && ((*cp == ' ') || (*cp == '\t')) ) + { + cp++; + } + while ( (cp < random_buffer + nread) && + (*cp != ' ') && (*cp != '\t') && (*cp != ';') ) + { + *np++ = *cp++; + } + *np = 0; + coding_system + = Ffind_coding_system (intern ((char *) coding_system_name)); + break; + } + } + if (EQ(coding_system, Qnil)) + do{ + if (detect_coding_type (&decst, random_buffer, nread, + XCODING_SYSTEM_TYPE (*codesys_in_out) + != CODESYS_AUTODETECT)) + break; + nread = Lstream_read (stream, + random_buffer, sizeof (random_buffer)); + if (!nread) + break; + } while(1); } - *eol_type_in_out = decst.eol_type; if (XCODING_SYSTEM_TYPE (*codesys_in_out) == CODESYS_AUTODETECT) - *codesys_in_out = coding_system_from_mask (decst.mask); + { + if (EQ(coding_system, Qnil)) + *codesys_in_out = coding_system_from_mask (decst.mask); + else + *codesys_in_out = coding_system; + } } - /* If we absolutely can't determine the EOL type, just assume LF. */ if (*eol_type_in_out == EOL_AUTODETECT) *eol_type_in_out = EOL_LF; @@ -1697,10 +1775,10 @@ #endif for (i = CODING_CATEGORY_LAST; i >= 0; i--) { - int sys = coding_category_by_priority[i]; + int sys = fcd->coding_category_by_priority[i]; if (decst.mask & (1 << sys)) { - Lisp_Object codesys = coding_category_system[sys]; + Lisp_Object codesys = fcd->coding_category_system[sys]; if (!NILP (codesys)) codesys = subsidiary_coding_system (codesys, decst.eol_type); val = Fcons (codesys, val); @@ -1836,6 +1914,9 @@ /* Additional information (the state of the running CCL program) used by the CCL decoder. */ struct ccl_program ccl; + + /* counter for UTF-8 or UCS-4 */ + unsigned char counter; #endif struct detection_state decst; }; @@ -1847,14 +1928,13 @@ static int decoding_flusher (Lstream *stream); static int decoding_closer (Lstream *stream); -static Lisp_Object decoding_marker (Lisp_Object stream, - void (*markobj) (Lisp_Object)); +static Lisp_Object decoding_marker (Lisp_Object stream); DEFINE_LSTREAM_IMPLEMENTATION ("decoding", lstream_decoding, sizeof (struct decoding_stream)); static Lisp_Object -decoding_marker (Lisp_Object stream, void (*markobj) (Lisp_Object)) +decoding_marker (Lisp_Object stream) { Lstream *str = DECODING_STREAM_DATA (XLSTREAM (stream))->other_end; Lisp_Object str_obj; @@ -1864,9 +1944,9 @@ and automatically marked. */ XSETLSTREAM (str_obj, str); - markobj (str_obj); + mark_object (str_obj); if (str->imp->marker) - return (str->imp->marker) (str_obj, markobj); + return (str->imp->marker) (str_obj); else return Qnil; } @@ -1970,6 +2050,7 @@ { setup_ccl_program (&str->ccl, CODING_SYSTEM_CCL_DECODE (str->codesys)); } + str->counter = 0; #endif /* MULE */ str->flags = str->ch = 0; } @@ -2302,14 +2383,13 @@ static int encoding_flusher (Lstream *stream); static int encoding_closer (Lstream *stream); -static Lisp_Object encoding_marker (Lisp_Object stream, - void (*markobj) (Lisp_Object)); +static Lisp_Object encoding_marker (Lisp_Object stream); DEFINE_LSTREAM_IMPLEMENTATION ("encoding", lstream_encoding, sizeof (struct encoding_stream)); static Lisp_Object -encoding_marker (Lisp_Object stream, void (*markobj) (Lisp_Object)) +encoding_marker (Lisp_Object stream) { Lstream *str = ENCODING_STREAM_DATA (XLSTREAM (stream))->other_end; Lisp_Object str_obj; @@ -2319,9 +2399,9 @@ and automatically marked. */ XSETLSTREAM (str_obj, str); - markobj (str_obj); + mark_object (str_obj); if (str->imp->marker) - return (str->imp->marker) (str_obj, markobj); + return (str->imp->marker) (str_obj); else return Qnil; } @@ -3160,8 +3240,6 @@ /* */ /************************************************************************/ -Lisp_Object ucs_to_mule_table[65536]; -Lisp_Object mule_to_ucs_table; DEFUN ("set-ucs-char", Fset_ucs_char, 2, 2, 0, /* Map UCS-4 code CODE to Mule character CHARACTER. @@ -3176,9 +3254,9 @@ CHECK_INT (code); c = XINT (code); - if (c < sizeof (ucs_to_mule_table)) + if (c < sizeof (fcd->ucs_to_mule_table)) { - ucs_to_mule_table[c] = character; + fcd->ucs_to_mule_table[c] = character; return Qt; } else @@ -3188,9 +3266,9 @@ static Lisp_Object ucs_to_char (unsigned long code) { - if (code < sizeof (ucs_to_mule_table)) + if (code < sizeof (fcd->ucs_to_mule_table)) { - return ucs_to_mule_table[code]; + return fcd->ucs_to_mule_table[code]; } else if ((0xe00000 <= code) && (code <= 0xe00000 + 94 * 94 * 14)) { @@ -3343,31 +3421,33 @@ struct decoding_stream *str = DECODING_STREAM_DATA (decoding); unsigned int flags = str->flags; unsigned int ch = str->ch; + unsigned char counter = str->counter; while (n--) { unsigned char c = *src++; - switch (flags) + switch (counter) { case 0: ch = c; - flags = 3; + counter = 3; break; case 1: decode_ucs4 ( ( ch << 8 ) | c, dst); ch = 0; - flags = 0; + counter = 0; break; default: ch = ( ch << 8 ) | c; - flags--; + counter--; } } - if (flags & CODING_STATE_END) + if (counter & CODING_STATE_END) DECODE_OUTPUT_PARTIAL_CHAR (ch); str->flags = flags; str->ch = ch; + str->counter = counter; } static void @@ -3552,37 +3632,38 @@ unsigned int flags = str->flags; unsigned int ch = str->ch; eol_type_t eol_type = str->eol_type; + unsigned char counter = str->counter; while (n--) { unsigned char c = *src++; - switch (flags) + switch (counter) { case 0: if ( c >= 0xfc ) { ch = c & 0x01; - flags = 5; + counter = 5; } else if ( c >= 0xf8 ) { ch = c & 0x03; - flags = 4; + counter = 4; } else if ( c >= 0xf0 ) { ch = c & 0x07; - flags = 3; + counter = 3; } else if ( c >= 0xe0 ) { ch = c & 0x0f; - flags = 2; + counter = 2; } else if ( c >= 0xc0 ) { ch = c & 0x1f; - flags = 1; + counter = 1; } else { @@ -3594,11 +3675,11 @@ ch = ( ch << 6 ) | ( c & 0x3f ); decode_ucs4 (ch, dst); ch = 0; - flags = 0; + counter = 0; break; default: ch = ( ch << 6 ) | ( c & 0x3f ); - flags--; + counter--; } label_continue_loop:; } @@ -3608,6 +3689,7 @@ str->flags = flags; str->ch = ch; + str->counter = counter; } static void @@ -5444,7 +5526,6 @@ void syms_of_file_coding (void) { - defsymbol (&Qbuffer_file_coding_system, "buffer-file-coding-system"); deferror (&Qcoding_system_error, "coding-system-error", "Coding-system error", Qio_error); @@ -5484,7 +5565,7 @@ DEFSUBR (Fset_char_ucs); DEFSUBR (Fchar_ucs); #endif /* MULE */ - defsymbol (&Qcoding_system_p, "coding-system-p"); + defsymbol (&Qcoding_systemp, "coding-system-p"); defsymbol (&Qno_conversion, "no-conversion"); defsymbol (&Qraw_text, "raw-text"); #ifdef MULE @@ -5579,11 +5660,14 @@ { int i; + fcd = xnew (struct file_coding_dump); + dumpstruct (&fcd, &fcd_description); + /* Initialize to something reasonable ... */ for (i = 0; i <= CODING_CATEGORY_LAST; i++) { - coding_category_system[i] = Qnil; - coding_category_by_priority[i] = i; + fcd->coding_category_system[i] = Qnil; + fcd->coding_category_by_priority[i] = i; } Fprovide (intern ("file-coding")); @@ -5644,6 +5728,7 @@ make_lisp_hash_table (50, HASH_TABLE_NON_WEAK, HASH_TABLE_EQ); the_codesys_prop_dynarr = Dynarr_new (codesys_prop); + dumpstruct (&the_codesys_prop_dynarr, &codesys_prop_dynarr_description); #define DEFINE_CODESYS_PROP(Prop_Type, Sym) do \ { \ @@ -5697,7 +5782,7 @@ Fdefine_coding_system_alias (Qno_conversion, Qraw_text); /* Need this for bootstrapping */ - coding_category_system[CODING_CATEGORY_NO_CONVERSION] = + fcd->coding_category_system[CODING_CATEGORY_NO_CONVERSION] = Fget_coding_system (Qraw_text); #ifdef MULE @@ -5705,7 +5790,7 @@ unsigned int i; for (i = 0; i < 65536; i++) - ucs_to_mule_table[i] = Qnil; + fcd->ucs_to_mule_table[i] = Qnil; } staticpro (&mule_to_ucs_table); mule_to_ucs_table = Fmake_char_table(Qgeneric); diff -r 28d9c139be4c -r 11054d720c21 src/file-coding.h --- a/src/file-coding.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/file-coding.h Mon Aug 13 11:26:11 2007 +0200 @@ -140,7 +140,6 @@ #define XCODING_SYSTEM(x) XRECORD (x, coding_system, struct Lisp_Coding_System) #define XSETCODING_SYSTEM(x, p) XSETRECORD (x, p, coding_system) #define CODING_SYSTEMP(x) RECORDP (x, coding_system) -#define GC_CODING_SYSTEMP(x) GC_RECORDP (x, coding_system) #define CHECK_CODING_SYSTEM(x) CHECK_RECORD (x, coding_system) #define CONCHECK_CODING_SYSTEM(x) CONCHECK_RECORD (x, coding_system) @@ -250,9 +249,9 @@ EXFUN (Fsubsidiary_coding_system, 2); extern Lisp_Object Qucs4, Qutf8; -extern Lisp_Object Qbig5, Qbuffer_file_coding_system, Qccl, Qcharset_g0; +extern Lisp_Object Qbig5, Qccl, Qcharset_g0; extern Lisp_Object Qcharset_g1, Qcharset_g2, Qcharset_g3, Qcoding_system_error; -extern Lisp_Object Qcoding_system_p, Qcr, Qcrlf, Qctext, Qdecode, Qencode; +extern Lisp_Object Qcoding_systemp, Qcr, Qcrlf, Qctext, Qdecode, Qencode; extern Lisp_Object Qeol_cr, Qeol_crlf, Qeol_lf, Qeol_type, Qescape_quoted; extern Lisp_Object Qforce_g0_on_output, Qforce_g1_on_output; extern Lisp_Object Qforce_g2_on_output, Qforce_g3_on_output; diff -r 28d9c139be4c -r 11054d720c21 src/fileio.c --- a/src/fileio.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/fileio.c Mon Aug 13 11:26:11 2007 +0200 @@ -71,7 +71,7 @@ /* Need to lower-case the drive letter, or else expanded filenames will sometimes compare inequal, because `expand-file-name' doesn't always down-case the drive letter. */ -#define DRIVE_LETTER(x) (tolower (x)) +#define DRIVE_LETTER(x) tolower (x) #endif /* WINDOWSNT */ int lisp_to_time (Lisp_Object, time_t *); @@ -109,8 +109,6 @@ int disable_auto_save_when_buffer_shrinks; -Lisp_Object Qfile_name_handler_alist; - Lisp_Object Vdirectory_sep_char; /* These variables describe handlers that have "already" had a chance @@ -1303,19 +1301,19 @@ { char resolved_path[MAXPATHLEN]; - char path[MAXPATHLEN]; - char *p = path; - int elen = XSTRING_LENGTH (expanded_name); - - if (elen >= countof (path)) + Extbyte *path; + Extbyte *p; + Extcount elen = XSTRING_LENGTH (expanded_name); + + GET_STRING_FILENAME_DATA_ALLOCA (expanded_name,path,elen); + p = path; + if (elen > MAXPATHLEN) goto toolong; - - memcpy (path, XSTRING_DATA (expanded_name), elen + 1); - /* memset (resolved_path, 0, sizeof (resolved_path)); */ - + /* Try doing it all at once. */ - /* !!#### Does realpath() Mule-encapsulate? */ - if (!xrealpath (path, resolved_path)) + /* !! Does realpath() Mule-encapsulate? + Answer: Nope! So we do it above */ + if (!xrealpath ((char *) path, resolved_path)) { /* Didn't resolve it -- have to do it one component at a time. */ /* "realpath" is a typically useless, stupid un*x piece of crap. @@ -1325,12 +1323,12 @@ partial result returned. What a piece of junk. */ for (;;) { - p = (char *) memchr (p + 1, '/', elen - (p + 1 - path)); + p = (Extbyte *) memchr (p + 1, '/', elen - (p + 1 - path)); if (p) *p = 0; /* memset (resolved_path, 0, sizeof (resolved_path)); */ - if (xrealpath (path, resolved_path)) + if (xrealpath ((char *) path, resolved_path)) { if (p) *p = '/'; @@ -1998,7 +1996,7 @@ Fcopy_file (filename, newname, /* We have already prompted if it was an integer, so don't have copy-file prompt again. */ - ((NILP (ok_if_already_exists)) ? Qnil : Qt), + (NILP (ok_if_already_exists) ? Qnil : Qt), Qt); Fdelete_file (filename); } @@ -3909,7 +3907,7 @@ run_hook (Qauto_save_hook); - if (GC_STRINGP (Vauto_save_list_file_name)) + if (STRINGP (Vauto_save_list_file_name)) listfile = condition_case_1 (Qt, auto_save_expand_name, Vauto_save_list_file_name, @@ -3928,13 +3926,13 @@ for (do_handled_files = 0; do_handled_files < 2; do_handled_files++) { for (tail = Vbuffer_alist; - GC_CONSP (tail); + CONSP (tail); tail = XCDR (tail)) { buf = XCDR (XCAR (tail)); b = XBUFFER (buf); - if (!GC_NILP (current_only) + if (!NILP (current_only) && b != current_buffer) continue; @@ -3946,7 +3944,7 @@ /* Check for auto save enabled and file changed since last auto save and file changed since last real save. */ - if (GC_STRINGP (b->auto_save_file_name) + if (STRINGP (b->auto_save_file_name) && BUF_SAVE_MODIFF (b) < BUF_MODIFF (b) && b->auto_save_modified < BUF_MODIFF (b) /* -1 means we've turned off autosaving for a while--see below. */ @@ -3991,7 +3989,7 @@ continue; } set_buffer_internal (b); - if (!auto_saved && GC_NILP (no_message)) + if (!auto_saved && NILP (no_message)) { static CONST unsigned char *msg = (CONST unsigned char *) "Auto-saving..."; @@ -4003,7 +4001,7 @@ /* Open the auto-save list file, if necessary. We only do this now so that the file only exists if we actually auto-saved any files. */ - if (!auto_saved && GC_STRINGP (listfile) && listdesc < 0) + if (!auto_saved && STRINGP (listfile) && listdesc < 0) { listdesc = open ((char *) XSTRING_DATA (listfile), O_WRONLY | O_TRUNC | O_CREAT | OPEN_BINARY, @@ -4092,7 +4090,7 @@ one because nothing needed to be auto-saved. Do this afterwards rather than before in case we get a crash attempting to autosave (in that case we'd still want the old one around). */ - if (listdesc < 0 && !auto_saved && GC_STRINGP (listfile)) + if (listdesc < 0 && !auto_saved && STRINGP (listfile)) unlink ((char *) XSTRING_DATA (listfile)); /* Show "...done" only if the echo area would otherwise be empty. */ @@ -4180,7 +4178,6 @@ defsymbol (&Qset_visited_file_modtime, "set-visited-file-modtime"); defsymbol (&Qcar_less_than_car, "car-less-than-car"); /* Vomitous! */ - defsymbol (&Qfile_name_handler_alist, "file-name-handler-alist"); defsymbol (&Qauto_save_hook, "auto-save-hook"); defsymbol (&Qauto_save_error, "auto-save-error"); defsymbol (&Qauto_saving, "auto-saving"); diff -r 28d9c139be4c -r 11054d720c21 src/filelock.c --- a/src/filelock.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/filelock.c Mon Aug 13 11:26:11 2007 +0200 @@ -126,11 +126,11 @@ char *lock_info_str; if (STRINGP (Fuser_login_name (Qnil))) - user_name = (char *)XSTRING_DATA((Fuser_login_name (Qnil))); + user_name = (char *) XSTRING_DATA (Fuser_login_name (Qnil)); else user_name = ""; if (STRINGP (Fsystem_name ())) - host_name = (char *)XSTRING_DATA((Fsystem_name ())); + host_name = (char *) XSTRING_DATA (Fsystem_name ()); else host_name = ""; lock_info_str = (char *)alloca (strlen (user_name) + strlen (host_name) diff -r 28d9c139be4c -r 11054d720c21 src/floatfns.c --- a/src/floatfns.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/floatfns.c Mon Aug 13 11:26:11 2007 +0200 @@ -108,15 +108,15 @@ #define arith_error(op,arg) \ - Fsignal (Qarith_error, list2 (build_string ((op)), (arg))) + Fsignal (Qarith_error, list2 (build_string (op), arg)) #define range_error(op,arg) \ - Fsignal (Qrange_error, list2 (build_string ((op)), (arg))) + Fsignal (Qrange_error, list2 (build_string (op), arg)) #define range_error2(op,a1,a2) \ - Fsignal (Qrange_error, list3 (build_string ((op)), (a1), (a2))) + Fsignal (Qrange_error, list3 (build_string (op), a1, a2)) #define domain_error(op,arg) \ - Fsignal (Qdomain_error, list2 (build_string ((op)), (arg))) + Fsignal (Qdomain_error, list2 (build_string (op), arg)) #define domain_error2(op,a1,a2) \ - Fsignal (Qdomain_error, list3 (build_string ((op)), (a1), (a2))) + Fsignal (Qdomain_error, list3 (build_string (op), a1, a2)) /* Convert float to Lisp Integer if it fits, else signal a range @@ -160,7 +160,7 @@ static Lisp_Object -mark_float (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_float (Lisp_Object obj) { return Qnil; } diff -r 28d9c139be4c -r 11054d720c21 src/fns.c --- a/src/fns.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/fns.c Mon Aug 13 11:26:11 2007 +0200 @@ -61,7 +61,7 @@ static int internal_old_equal (Lisp_Object, Lisp_Object, int); static Lisp_Object -mark_bit_vector (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_bit_vector (Lisp_Object obj) { return Qnil; } @@ -69,10 +69,10 @@ static void print_bit_vector (Lisp_Object obj, Lisp_Object printcharfun, int escapeflag) { - int i; + size_t i; struct Lisp_Bit_Vector *v = XBIT_VECTOR (obj); - int len = bit_vector_length (v); - int last = len; + size_t len = bit_vector_length (v); + size_t last = len; if (INTP (Vprint_length)) last = min (len, XINT (Vprint_length)); @@ -111,9 +111,16 @@ sizeof (long))); } +static const struct lrecord_description bit_vector_description[] = { + { XD_LISP_OBJECT, offsetof(Lisp_Bit_Vector, next), 1 }, + { XD_END } +}; + + DEFINE_BASIC_LRECORD_IMPLEMENTATION ("bit-vector", bit_vector, mark_bit_vector, print_bit_vector, 0, - bit_vector_equal, bit_vector_hash, 0, + bit_vector_equal, bit_vector_hash, + bit_vector_description, struct Lisp_Bit_Vector); DEFUN ("identity", Fidentity, 1, 1, 0, /* @@ -208,7 +215,7 @@ return make_int (XSTRING_CHAR_LENGTH (sequence)); else if (CONSP (sequence)) { - int len; + size_t len; GET_EXTERNAL_LIST_LENGTH (sequence, len); return make_int (len); } @@ -235,7 +242,7 @@ (list)) { Lisp_Object hare, tortoise; - int len; + size_t len; for (hare = tortoise = list, len = 0; CONSP (hare) && (! EQ (hare, tortoise) || len == 0); @@ -515,7 +522,7 @@ Lisp_Object list_copy = Fcons (XCAR (list), XCDR (list)); Lisp_Object last = list_copy; Lisp_Object hare, tortoise; - int len; + size_t len; for (tortoise = hare = XCDR (list), len = 1; CONSP (hare); @@ -916,7 +923,7 @@ */ (seq, from, to)) { - int len, f, t; + EMACS_INT len, f, t; if (STRINGP (seq)) return Fsubstring (seq, from, to); @@ -950,7 +957,7 @@ if (VECTORP (seq)) { Lisp_Object result = make_vector (t - f, Qnil); - int i; + EMACS_INT i; Lisp_Object *in_elts = XVECTOR_DATA (seq); Lisp_Object *out_elts = XVECTOR_DATA (result); @@ -962,7 +969,7 @@ if (LISTP (seq)) { Lisp_Object result = Qnil; - int i; + EMACS_INT i; seq = Fnthcdr (make_int (f), seq); @@ -978,7 +985,7 @@ /* bit vector */ { Lisp_Object result = make_bit_vector (t - f, Qzero); - int i; + EMACS_INT i; for (i = f; i < t; i++) set_bit_vector_bit (XBIT_VECTOR (result), i - f, @@ -993,7 +1000,7 @@ */ (n, list)) { - REGISTER int i; + REGISTER size_t i; REGISTER Lisp_Object tail = list; CHECK_NATNUM (n); for (i = XINT (n); i; i--) @@ -1052,7 +1059,7 @@ #ifdef LOSING_BYTECODE else if (COMPILED_FUNCTIONP (sequence)) { - int idx = XINT (n); + EMACS_INT idx = XINT (n); if (idx < 0) { lose: @@ -1104,7 +1111,7 @@ */ (list, n)) { - int int_n, count; + EMACS_INT int_n, count; Lisp_Object retval, tortoise, hare; CHECK_LIST (list); @@ -1140,7 +1147,7 @@ */ (list, n)) { - int int_n; + EMACS_INT int_n; CHECK_LIST (list); @@ -2714,12 +2721,6 @@ return value; } -void -pure_put (Lisp_Object sym, Lisp_Object prop, Lisp_Object val) -{ - Fput (sym, prop, Fpurecopy (val)); -} - DEFUN ("remprop", Fremprop, 2, 2, 0, /* Remove from OBJECT's property list the property PROPNAME and its value. OBJECT can be a symbol, face, extent, or string. Returns @@ -3176,11 +3177,14 @@ return result; } -DEFUN ("mapc", Fmapc, 2, 2, 0, /* +DEFUN ("mapc-internal", Fmapc_internal, 2, 2, 0, /* Apply FUNCTION to each element of SEQUENCE. SEQUENCE may be a list, a vector, a bit vector, or a string. This function is like `mapcar' but does not accumulate the results, which is more efficient if you do not use the results. + +The difference between this and `mapc' is that `mapc' supports all +the spiffy Common Lisp arguments. You should normally use `mapc'. */ (fn, seq)) { @@ -3871,7 +3875,7 @@ DEFSUBR (Fnconc); DEFSUBR (Fmapcar); DEFSUBR (Fmapvector); - DEFSUBR (Fmapc); + DEFSUBR (Fmapc_internal); DEFSUBR (Fmapconcat); DEFSUBR (Fload_average); DEFSUBR (Ffeaturep); diff -r 28d9c139be4c -r 11054d720c21 src/font-lock.c --- a/src/font-lock.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/font-lock.c Mon Aug 13 11:26:11 2007 +0200 @@ -769,8 +769,14 @@ } void -vars_of_font_lock (void) +reinit_vars_of_font_lock (void) { xzero (context_cache); xzero (bol_context_cache); } + +void +vars_of_font_lock (void) +{ + reinit_vars_of_font_lock (); +} diff -r 28d9c139be4c -r 11054d720c21 src/frame-msw.c --- a/src/frame-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/frame-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -248,13 +248,13 @@ } static void -mswindows_mark_frame (struct frame *f, void (*markobj) (Lisp_Object)) +mswindows_mark_frame (struct frame *f) { - markobj (FRAME_MSWINDOWS_MENU_HASH_TABLE (f)); + mark_object (FRAME_MSWINDOWS_MENU_HASH_TABLE (f)); #ifdef HAVE_TOOLBARS - markobj (FRAME_MSWINDOWS_TOOLBAR_HASH_TABLE (f)); + mark_object (FRAME_MSWINDOWS_TOOLBAR_HASH_TABLE (f)); #endif - markobj (FRAME_MSWINDOWS_WIDGET_HASH_TABLE (f)); + mark_object (FRAME_MSWINDOWS_WIDGET_HASH_TABLE (f)); } static void @@ -741,10 +741,16 @@ } void -vars_of_frame_mswindows (void) +reinit_vars_of_frame_mswindows (void) { /* Needn't staticpro -- see comment above. */ Vmswindows_frame_being_created = Qnil; +} + +void +vars_of_frame_mswindows (void) +{ + reinit_vars_of_frame_mswindows (); DEFVAR_LISP ("mswindows-use-system-frame-size-defaults", &Vmswindows_use_system_frame_size_defaults /* Controls whether to use system or XEmacs defaults for frame size. diff -r 28d9c139be4c -r 11054d720c21 src/frame-x.c --- a/src/frame-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/frame-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -103,19 +103,34 @@ struct frame * x_any_window_to_frame (struct device *d, Window wdesc) { + Widget w; + assert (DEVICE_X_P (d)); + + w = XtWindowToWidget (DEVICE_X_DISPLAY (d), wdesc); + + if (!w) + return 0; + + /* We used to map over all frames here and then map over all widgets + belonging to that frame. However it turns out that this was very fragile + as it requires our display stuctures to be in sync _and_ that the + loop is told about every new widget somebody adds. Therefore we + now let Xt find it for us (which does a bottom-up search which + could even be faster) */ + return x_any_widget_or_parent_to_frame (d, w); +} + +static struct frame * +x_find_frame_for_window (struct device *d, Window wdesc) +{ Lisp_Object tail, frame; struct frame *f; - - assert (DEVICE_X_P (d)); - /* This function was previously written to accept only a window argument (and to loop over all devices looking for a matching window), but that is incorrect because window ID's are not unique across displays. */ for (tail = DEVICE_FRAME_LIST (d); CONSP (tail); tail = XCDR (tail)) { - int i; - frame = XCAR (tail); f = XFRAME (frame); /* This frame matches if the window is any of its widgets. */ @@ -138,18 +153,18 @@ would incorrectly get sucked away by Emacs if this function matched on psheet widgets. */ - for (i = 0; i < FRAME_X_NUM_TOP_WIDGETS (f); i++) - { - Widget wid = FRAME_X_TOP_WIDGETS (f)[i]; - if (wid && XtIsManaged (wid) && wdesc == XtWindow (wid)) - return f; - } - -#ifdef HAVE_SCROLLBARS - /* Match if the window is one of this frame's scrollbars. */ - if (x_window_is_scrollbar (f, wdesc)) - return f; -#endif + /* Note: that this called only from + x_any_widget_or_parent_to_frame it is unnecessary to iterate + over the top level widgets. */ + + /* Note: we use to special case scrollbars but this turns out to be a bad idea + because + 1. We sometimes get events for _unmapped_ scrollbars and our + callers don't want us to fail. + 2. Starting with the 21.2 widget stuff there are now loads of + widgets to check and it is easy to forget adding them in a loop here. + See x_any_window_to_frame + 3. We pick up all widgets now anyway. */ } return 0; @@ -160,7 +175,7 @@ { while (widget) { - struct frame *f = x_any_window_to_frame (d, XtWindow (widget)); + struct frame *f = x_find_frame_for_window (d, XtWindow (widget)); if (f) return f; widget = XtParent (widget); @@ -421,9 +436,9 @@ init_x_prop_symbols (void) { #define def(sym, rsrc) \ - pure_put (sym, Qx_resource_name, build_string (rsrc)) + Fput (sym, Qx_resource_name, build_string (rsrc)) #define defi(sym,rsrc) \ - def (sym, rsrc); pure_put (sym, Qintegerp, Qt) + def (sym, rsrc); Fput (sym, Qintegerp, Qt) #if 0 /* this interferes with things. #### fix this right */ def (Qminibuffer, XtNminibuffer); @@ -1880,7 +1895,7 @@ char *string; CHECK_STRING (lisp_window_id); - string = (char *) (XSTRING_DATA (lisp_window_id)); + string = (char *) XSTRING_DATA (lisp_window_id); if (string[0] == '0' && (string[1] == 'x' || string[1] == 'X')) sscanf (string+2, "%lxu", &window_id); #if 0 @@ -2190,10 +2205,10 @@ } static void -x_mark_frame (struct frame *f, void (*markobj) (Lisp_Object)) +x_mark_frame (struct frame *f) { - markobj (FRAME_X_ICON_PIXMAP (f)); - markobj (FRAME_X_ICON_PIXMAP_MASK (f)); + mark_object (FRAME_X_ICON_PIXMAP (f)); + mark_object (FRAME_X_ICON_PIXMAP_MASK (f)); } static void diff -r 28d9c139be4c -r 11054d720c21 src/frame.c --- a/src/frame.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/frame.c Mon Aug 13 11:26:11 2007 +0200 @@ -86,7 +86,6 @@ Lisp_Object Qborder_width; Lisp_Object Qframep, Qframe_live_p; -Lisp_Object Qframe_x_p, Qframe_tty_p; Lisp_Object Qdelete_frame; Lisp_Object Qframe_title_format, Vframe_title_format; @@ -122,17 +121,17 @@ static Lisp_Object -mark_frame (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_frame (Lisp_Object obj) { struct frame *f = XFRAME (obj); -#define MARKED_SLOT(x) ((void) (markobj (f->x))); +#define MARKED_SLOT(x) mark_object (f->x) #include "frameslots.h" - mark_subwindow_cachels (f->subwindow_cachels, markobj); + mark_subwindow_cachels (f->subwindow_cachels); if (FRAME_LIVE_P (f)) /* device is nil for a dead frame */ - MAYBE_FRAMEMETH (f, mark_frame, (f, markobj)); + MAYBE_FRAMEMETH (f, mark_frame, (f)); return Qnil; } @@ -162,7 +161,7 @@ static void nuke_all_frame_slots (struct frame *f) { -#define MARKED_SLOT(x) f->x = Qnil; +#define MARKED_SLOT(x) f->x = Qnil #include "frameslots.h" } @@ -209,6 +208,10 @@ /* cache of subwindows visible on frame */ f->subwindow_cachels = Dynarr_new (subwindow_cachel); + /* associated exposure ignore list */ + f->subwindow_exposures = 0; + f->subwindow_exposures_tail = 0; + /* Choose a buffer for the frame's root window. */ XWINDOW (root_window)->buffer = Qt; { @@ -410,7 +413,7 @@ update_frame_window_mirror (f); - if (initialized) + if (initialized && !DEVICE_STREAM_P (d)) { if (!NILP (f->minibuffer_window)) reset_face_cachels (XWINDOW (f->minibuffer_window)); @@ -3074,8 +3077,6 @@ defsymbol (&Qframep, "framep"); defsymbol (&Qframe_live_p, "frame-live-p"); - defsymbol (&Qframe_x_p, "frame-x-p"); - defsymbol (&Qframe_tty_p, "frame-tty-p"); defsymbol (&Qdelete_frame, "delete-frame"); defsymbol (&Qsynchronize_minibuffers, "synchronize-minibuffers"); defsymbol (&Qbuffer_predicate, "buffer-predicate"); @@ -3291,13 +3292,13 @@ This is the same format as `modeline-format' with the exception that %- is ignored. */ ); - Vframe_title_format = Fpurecopy (build_string ("%S: %b")); + Vframe_title_format = build_string ("%S: %b"); DEFVAR_LISP ("frame-icon-title-format", &Vframe_icon_title_format /* Controls the title of the icon corresponding to the selected frame. See also the variable `frame-title-format'. */ ); - Vframe_icon_title_format = Fpurecopy (build_string ("%b")); + Vframe_icon_title_format = build_string ("%b"); DEFVAR_LISP ("default-frame-name", &Vdefault_frame_name /* The default name to assign to newly-created frames. @@ -3305,9 +3306,9 @@ This must be a string. */ ); #ifndef INFODOCK - Vdefault_frame_name = Fpurecopy (build_string ("emacs")); + Vdefault_frame_name = build_string ("emacs"); #else - Vdefault_frame_name = Fpurecopy (build_string ("InfoDock")); + Vdefault_frame_name = build_string ("InfoDock"); #endif DEFVAR_LISP ("default-frame-plist", &Vdefault_frame_plist /* diff -r 28d9c139be4c -r 11054d720c21 src/frame.h --- a/src/frame.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/frame.h Mon Aug 13 11:26:11 2007 +0200 @@ -94,6 +94,9 @@ /* subwindow cache elements for this frame */ subwindow_cachel_dynarr *subwindow_cachels; + struct expose_ignore* subwindow_exposures; + struct expose_ignore* subwindow_exposures_tail; + #ifdef HAVE_SCROLLBARS /* frame-local scrollbar information. See scrollbar.c. */ int scrollbar_y_offset; @@ -178,6 +181,7 @@ unsigned int faces_changed :1; unsigned int frame_changed :1; unsigned int subwindows_changed :1; + unsigned int subwindows_state_changed :1; unsigned int glyphs_changed :1; unsigned int icon_changed :1; unsigned int menubar_changed :1; @@ -233,7 +237,6 @@ #define XFRAME(x) XRECORD (x, frame, struct frame) #define XSETFRAME(x, p) XSETRECORD (x, p, frame) #define FRAMEP(x) RECORDP (x, frame) -#define GC_FRAMEP(x) GC_RECORDP (x, frame) #define CHECK_FRAME(x) CHECK_RECORD (x, frame) #define CONCHECK_FRAME(x) CONCHECK_RECORD (x, frame) @@ -260,7 +263,7 @@ return f; } # define FRAME_TYPE_DATA(f, type) \ - ((struct type##_frame *) (error_check_frame_type (f, Q##type))->frame_data) + ((struct type##_frame *) error_check_frame_type (f, Q##type)->frame_data) #else # define FRAME_TYPE_DATA(f, type) \ ((struct type##_frame *) (f)->frame_data) @@ -340,6 +343,19 @@ subwindows_changed = 1; \ } while (0) +#define MARK_FRAME_SUBWINDOWS_STATE_CHANGED(f) do { \ + struct frame *mfgc_f = (f); \ + mfgc_f->subwindows_state_changed = 1; \ + mfgc_f->modiff++; \ + if (!NILP (mfgc_f->device)) \ + { \ + struct device *mfgc_d = XDEVICE (mfgc_f->device); \ + MARK_DEVICE_SUBWINDOWS_STATE_CHANGED (mfgc_d); \ + } \ + else \ + subwindows_state_changed = 1; \ +} while (0) + #define MARK_FRAME_TOOLBARS_CHANGED(f) do { \ struct frame *mftc_f = (f); \ mftc_f->toolbar_changed = 1; \ diff -r 28d9c139be4c -r 11054d720c21 src/free-hook.c --- a/src/free-hook.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/free-hook.c Mon Aug 13 11:26:11 2007 +0200 @@ -85,14 +85,14 @@ /* System function prototypes don't belong in C source files */ /* extern void free (void *); */ -struct hash_table *pointer_table; +static struct hash_table *pointer_table; extern void (*__free_hook) (void *); extern void *(*__malloc_hook) (size_t); static void *check_malloc (size_t); -typedef void (*fun_ptr) (); +typedef void (*fun_ptr) (void); /* free_queue is not too useful without backtrace logging */ #define FREE_QUEUE_LIMIT 1 @@ -110,11 +110,11 @@ unsigned long length; } free_queue_entry; -free_queue_entry free_queue[FREE_QUEUE_LIMIT]; +static free_queue_entry free_queue[FREE_QUEUE_LIMIT]; -int current_free; +static int current_free; -int strict_free_check; +static int strict_free_check; static void check_free (void *ptr) diff -r 28d9c139be4c -r 11054d720c21 src/gdbinit --- a/src/gdbinit Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gdbinit Mon Aug 13 11:26:11 2007 +0200 @@ -327,8 +327,8 @@ if $imp == &lrecord_opaque pstruct Lisp_Opaque else - if $imp == &lrecord_opaque_list - pstruct Lisp_Opaque_List + if $imp == &lrecord_opaque_ptr + pstruct Lisp_Opaque_Ptr else if $imp == &lrecord_popup_data pstruct popup_data diff -r 28d9c139be4c -r 11054d720c21 src/general.c --- a/src/general.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/general.c Mon Aug 13 11:26:11 2007 +0200 @@ -34,24 +34,19 @@ Lisp_Object Qactually_requested; Lisp_Object Qafter; Lisp_Object Qall; -Lisp_Object Qalways; Lisp_Object Qand; Lisp_Object Qassoc; Lisp_Object Qat; -Lisp_Object Qauth; Lisp_Object Qautodetect; Lisp_Object Qbad_variable; -Lisp_Object Qbase; Lisp_Object Qbefore; Lisp_Object Qbinary; -Lisp_Object Qbinddn; Lisp_Object Qbitmap; -Lisp_Object Qblack; Lisp_Object Qboolean; Lisp_Object Qbottom; Lisp_Object Qbuffer; Lisp_Object Qbutton; -Lisp_Object Qcase; +Lisp_Object Qcenter; Lisp_Object Qcategory; Lisp_Object Qchannel; Lisp_Object Qchar; @@ -68,7 +63,6 @@ Lisp_Object Qdefault; Lisp_Object Qdelete; Lisp_Object Qdelq; -Lisp_Object Qderef; Lisp_Object Qdevice; Lisp_Object Qdimension; Lisp_Object Qdisplay; @@ -81,7 +75,6 @@ Lisp_Object Qeval; Lisp_Object Qextents; Lisp_Object Qface; -Lisp_Object Qfind; Lisp_Object Qfont; Lisp_Object Qframe; Lisp_Object Qfunction; @@ -92,6 +85,7 @@ Lisp_Object Qgutter; Lisp_Object Qheight; Lisp_Object Qhighlight; +Lisp_Object Qhorizontal; Lisp_Object Qicon; Lisp_Object Qid; Lisp_Object Qimage; @@ -101,10 +95,7 @@ Lisp_Object Qinternal; Lisp_Object Qkey; Lisp_Object Qkey_assoc; -Lisp_Object Qkeyboard; Lisp_Object Qkeymap; -Lisp_Object Qkrbv41; -Lisp_Object Qkrbv42; Lisp_Object Qleft; Lisp_Object Qlist; Lisp_Object Qmagic; @@ -112,14 +103,12 @@ Lisp_Object Qmarkers; Lisp_Object Qmax; Lisp_Object Qmemory; -Lisp_Object Qmenubar; Lisp_Object Qmessage; Lisp_Object Qminus; Lisp_Object Qmodifiers; Lisp_Object Qmotion; Lisp_Object Qmswindows; Lisp_Object Qname; -Lisp_Object Qnever; Lisp_Object Qnone; Lisp_Object Qnot; Lisp_Object Qnothing; @@ -130,15 +119,11 @@ Lisp_Object Qold_delq; Lisp_Object Qold_rassoc; Lisp_Object Qold_rassq; -Lisp_Object Qonelevel; Lisp_Object Qonly; Lisp_Object Qor; Lisp_Object Qother; -Lisp_Object Qpasswd; -Lisp_Object Qpath; Lisp_Object Qpointer; Lisp_Object Qpopup; -Lisp_Object Qport; Lisp_Object Qprint; Lisp_Object Qprocess; Lisp_Object Qprovide; @@ -154,17 +139,14 @@ Lisp_Object Qsignal; Lisp_Object Qsimple; Lisp_Object Qsize; -Lisp_Object Qsizelimit; Lisp_Object Qspace; Lisp_Object Qspecifier; Lisp_Object Qstream; Lisp_Object Qstring; -Lisp_Object Qsubtree; Lisp_Object Qsymbol; Lisp_Object Qsyntax; Lisp_Object Qtest; Lisp_Object Qtext; -Lisp_Object Qtimelimit; Lisp_Object Qtimeout; Lisp_Object Qtimestamp; Lisp_Object Qtoolbar; @@ -175,9 +157,8 @@ Lisp_Object Qundefined; Lisp_Object Qunimplemented; Lisp_Object Qvalue_assoc; -Lisp_Object Qvector; +Lisp_Object Qvertical; Lisp_Object Qwarning; -Lisp_Object Qwhite; Lisp_Object Qwidth; Lisp_Object Qwidget; Lisp_Object Qwindow; @@ -191,25 +172,20 @@ defsymbol (&Qactually_requested, "actually-requested"); defsymbol (&Qafter, "after"); defsymbol (&Qall, "all"); - defsymbol (&Qalways, "always"); defsymbol (&Qand, "and"); defsymbol (&Qassoc, "assoc"); defsymbol (&Qat, "at"); - defsymbol (&Qauth, "auth"); defsymbol (&Qautodetect, "autodetect"); defsymbol (&Qbad_variable, "bad-variable"); - defsymbol (&Qbase, "base"); defsymbol (&Qbefore, "before"); defsymbol (&Qbinary, "binary"); - defsymbol (&Qbinddn, "binddn"); defsymbol (&Qbitmap, "bitmap"); - defsymbol (&Qblack, "black"); defsymbol (&Qboolean, "boolean"); defsymbol (&Qbottom, "bottom"); defsymbol (&Qbuffer, "buffer"); defsymbol (&Qbutton, "button"); - defsymbol (&Qcase, "case"); defsymbol (&Qcategory, "category"); + defsymbol (&Qcenter, "center"); defsymbol (&Qchannel, "channel"); defsymbol (&Qchar, "char"); defsymbol (&Qcharacter, "character"); @@ -225,7 +201,6 @@ defsymbol (&Qdefault, "default"); defsymbol (&Qdelete, "delete"); defsymbol (&Qdelq, "delq"); - defsymbol (&Qderef, "deref"); defsymbol (&Qdevice, "device"); defsymbol (&Qdimension, "dimension"); defsymbol (&Qdisplay, "display"); @@ -238,7 +213,6 @@ defsymbol (&Qeval, "eval"); defsymbol (&Qextents, "extents"); defsymbol (&Qface, "face"); - defsymbol (&Qfind, "find"); defsymbol (&Qfont, "font"); defsymbol (&Qframe, "frame"); defsymbol (&Qfunction, "function"); @@ -249,6 +223,7 @@ defsymbol (&Qgutter, "gutter"); defsymbol (&Qheight, "height"); defsymbol (&Qhighlight, "highlight"); + defsymbol (&Qhorizontal, "horizontal"); defsymbol (&Qicon, "icon"); defsymbol (&Qid, "id"); defsymbol (&Qimage, "image"); @@ -258,10 +233,7 @@ defsymbol (&Qinternal, "internal"); defsymbol (&Qkey, "key"); defsymbol (&Qkey_assoc, "key-assoc"); - defsymbol (&Qkeyboard, "keyboard"); defsymbol (&Qkeymap, "keymap"); - defsymbol (&Qkrbv41, "krbv41"); - defsymbol (&Qkrbv42, "krbv42"); defsymbol (&Qleft, "left"); defsymbol (&Qlist, "list"); defsymbol (&Qmagic, "magic"); @@ -269,14 +241,12 @@ defsymbol (&Qmarkers, "markers"); defsymbol (&Qmax, "max"); defsymbol (&Qmemory, "memory"); - defsymbol (&Qmenubar, "menubar"); defsymbol (&Qmessage, "message"); defsymbol (&Qminus, "-"); defsymbol (&Qmodifiers, "modifiers"); defsymbol (&Qmotion, "motion"); defsymbol (&Qmswindows, "mswindows"); defsymbol (&Qname, "name"); - defsymbol (&Qnever, "never"); defsymbol (&Qnone, "none"); defsymbol (&Qnot, "not"); defsymbol (&Qnothing, "nothing"); @@ -287,15 +257,11 @@ defsymbol (&Qold_delq, "old-delq"); defsymbol (&Qold_rassoc, "old-rassoc"); defsymbol (&Qold_rassq, "old-rassq"); - defsymbol (&Qonelevel, "onelevel"); defsymbol (&Qonly, "only"); defsymbol (&Qor, "or"); defsymbol (&Qother, "other"); - defsymbol (&Qpasswd, "passwd"); - defsymbol (&Qpath, "path"); defsymbol (&Qpointer, "pointer"); defsymbol (&Qpopup, "popup"); - defsymbol (&Qport, "port"); defsymbol (&Qprint, "print"); defsymbol (&Qprocess, "process"); defsymbol (&Qprovide, "provide"); @@ -311,17 +277,14 @@ defsymbol (&Qsignal, "signal"); defsymbol (&Qsimple, "simple"); defsymbol (&Qsize, "size"); - defsymbol (&Qsizelimit, "sizelimit"); defsymbol (&Qspace, "space"); defsymbol (&Qspecifier, "specifier"); defsymbol (&Qstream, "stream"); defsymbol (&Qstring, "string"); - defsymbol (&Qsubtree, "subtree"); defsymbol (&Qsymbol, "symbol"); defsymbol (&Qsyntax, "syntax"); defsymbol (&Qtest, "test"); defsymbol (&Qtext, "text"); - defsymbol (&Qtimelimit, "timelimit"); defsymbol (&Qtimeout, "timeout"); defsymbol (&Qtimestamp, "timestamp"); defsymbol (&Qtoolbar, "toolbar"); @@ -332,9 +295,8 @@ defsymbol (&Qundefined, "undefined"); defsymbol (&Qunimplemented, "unimplemented"); defsymbol (&Qvalue_assoc, "value-assoc"); - defsymbol (&Qvector, "vector"); + defsymbol (&Qvertical, "vertical"); defsymbol (&Qwarning, "warning"); - defsymbol (&Qwhite, "white"); defsymbol (&Qwidth, "width"); defsymbol (&Qwidget, "widget"); defsymbol (&Qwindow, "window"); diff -r 28d9c139be4c -r 11054d720c21 src/getloadavg.c --- a/src/getloadavg.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/getloadavg.c Mon Aug 13 11:26:11 2007 +0200 @@ -94,10 +94,6 @@ #include -#ifndef errno -extern int errno; -#endif - #ifndef HAVE_GETLOADAVG /* The existing Emacs configuration files define a macro called diff -r 28d9c139be4c -r 11054d720c21 src/gif_io.c --- a/src/gif_io.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gif_io.c Mon Aug 13 11:26:11 2007 +0200 @@ -3,6 +3,7 @@ #include #include #include "gifrlib.h" +#include "sysfile.h" /****************************************************************************** * Set up the GifFileType structure for use. This must be called first in any * diff -r 28d9c139be4c -r 11054d720c21 src/glyphs-eimage.c --- a/src/glyphs-eimage.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/glyphs-eimage.c Mon Aug 13 11:26:11 2007 +0200 @@ -482,7 +482,7 @@ /* now instantiate */ MAYBE_DEVMETH (XDEVICE (ii->device), init_image_instance_from_eimage, - (ii, cinfo.output_width, cinfo.output_height, + (ii, cinfo.output_width, cinfo.output_height, 1, unwind.eimage, dest_mask, instantiator, domain)); @@ -651,10 +651,10 @@ DGifSlurp (unwind.giffile); } - /* 3. Now create the EImage */ + /* 3. Now create the EImage(s) */ { ColorMapObject *cmo = unwind.giffile->SColorMap; - int i, j, row, pass, interlace; + int i, j, row, pass, interlace, slice; unsigned char *eip; /* interlaced gifs have rows in this order: 0, 8, 16, ..., 4, 12, 20, ..., 2, 6, 10, ..., 1, 3, 5, ... */ @@ -663,52 +663,81 @@ height = unwind.giffile->SHeight; width = unwind.giffile->SWidth; - unwind.eimage = (unsigned char*) xmalloc (width * height * 3); + unwind.eimage = (unsigned char*) + xmalloc (width * height * 3 * unwind.giffile->ImageCount); if (!unwind.eimage) signal_image_error("Unable to allocate enough memory for image", instantiator); /* write the data in EImage format (8bit RGB triples) */ - /* Note: We just use the first image in the file and ignore the rest. - We check here that that image covers the full "screen" size. - I don't know whether that's always the case. - -dkindred@cs.cmu.edu */ - if (unwind.giffile->SavedImages[0].ImageDesc.Height != height - || unwind.giffile->SavedImages[0].ImageDesc.Width != width - || unwind.giffile->SavedImages[0].ImageDesc.Left != 0 - || unwind.giffile->SavedImages[0].ImageDesc.Top != 0) - signal_image_error ("First image in GIF file is not full size", - instantiator); - - interlace = unwind.giffile->SavedImages[0].ImageDesc.Interlace; - pass = 0; - row = interlace ? InterlacedOffset[pass] : 0; - eip = unwind.eimage; - for (i = 0; i < height; i++) + for (slice = 0; slice < unwind.giffile->ImageCount; slice++) { - if (interlace) - if (row >= height) { - row = InterlacedOffset[++pass]; - while (row >= height) - row = InterlacedOffset[++pass]; - } - eip = unwind.eimage + (row * width * 3); - for (j = 0; j < width; j++) + /* We check here that that the current image covers the full "screen" size. */ + if (unwind.giffile->SavedImages[slice].ImageDesc.Height != height + || unwind.giffile->SavedImages[slice].ImageDesc.Width != width + || unwind.giffile->SavedImages[slice].ImageDesc.Left != 0 + || unwind.giffile->SavedImages[slice].ImageDesc.Top != 0) + signal_image_error ("Image in GIF file is not full size", + instantiator); + + interlace = unwind.giffile->SavedImages[slice].ImageDesc.Interlace; + pass = 0; + row = interlace ? InterlacedOffset[pass] : 0; + eip = unwind.eimage + (width * height * 3 * slice); + for (i = 0; i < height; i++) { - unsigned char pixel = unwind.giffile->SavedImages[0].RasterBits[(i * width) + j]; - *eip++ = cmo->Colors[pixel].Red; - *eip++ = cmo->Colors[pixel].Green; - *eip++ = cmo->Colors[pixel].Blue; + if (interlace) + if (row >= height) { + row = InterlacedOffset[++pass]; + while (row >= height) + row = InterlacedOffset[++pass]; + } + eip = unwind.eimage + (width * height * 3 * slice) + (row * width * 3); + for (j = 0; j < width; j++) + { + unsigned char pixel = + unwind.giffile->SavedImages[slice].RasterBits[(i * width) + j]; + *eip++ = cmo->Colors[pixel].Red; + *eip++ = cmo->Colors[pixel].Green; + *eip++ = cmo->Colors[pixel].Blue; + } + row += interlace ? InterlacedJumps[pass] : 1; } - row += interlace ? InterlacedJumps[pass] : 1; } + + /* now instantiate */ + MAYBE_DEVMETH (XDEVICE (ii->device), + init_image_instance_from_eimage, + (ii, width, height, unwind.giffile->ImageCount, unwind.eimage, dest_mask, + instantiator, domain)); } - /* now instantiate */ - MAYBE_DEVMETH (XDEVICE (ii->device), - init_image_instance_from_eimage, - (ii, width, height, unwind.eimage, dest_mask, - instantiator, domain)); + + /* We read the gif successfully. If we have more than one slice then + animate the gif. */ + if (unwind.giffile->ImageCount > 1) + { + /* See if there is a timeout value. In theory there could be one + for every image - but that makes the implementation way to + complicated for now so we just take the first. */ + unsigned short timeout = 0; + Lisp_Object tid; + if (unwind.giffile->SavedImages[0].Function == GRAPHICS_EXT_FUNC_CODE + && + unwind.giffile->SavedImages[0].ExtensionBlockCount) + { + timeout = (unsigned short) + ((unwind.giffile->SavedImages[0].ExtensionBlocks[0].Bytes[2] << 8) + + unwind.giffile-> SavedImages[0].ExtensionBlocks[0].Bytes[1]) * 10; + } + + /* Too short a timeout will crucify us performance-wise. */ + tid = add_glyph_animated_timeout (timeout > 10 ? timeout : 10, image_instance); + + if (!NILP (tid)) + IMAGE_INSTANCE_PIXMAP_TIMEOUT (ii) = XINT (tid); + } + unbind_to (speccount, Qnil); } @@ -990,7 +1019,7 @@ /* now instantiate */ MAYBE_DEVMETH (XDEVICE (ii->device), init_image_instance_from_eimage, - (ii, width, height, unwind.eimage, dest_mask, + (ii, width, height, 1, unwind.eimage, dest_mask, instantiator, domain)); /* This will clean up everything else. */ @@ -1270,7 +1299,7 @@ /* now instantiate */ MAYBE_DEVMETH (XDEVICE (ii->device), init_image_instance_from_eimage, - (ii, width, height, unwind.eimage, dest_mask, + (ii, width, height, 1, unwind.eimage, dest_mask, instantiator, domain)); unbind_to (speccount, Qnil); diff -r 28d9c139be4c -r 11054d720c21 src/glyphs-msw.c --- a/src/glyphs-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/glyphs-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -1,5 +1,5 @@ /* mswindows-specific glyph objects. - Copyright (C) 1998, 99 Andy Piper. + Copyright (C) 1998, 1999 Andy Piper. This file is part of XEmacs. @@ -57,6 +57,7 @@ DECLARE_IMAGE_INSTANTIATOR_FORMAT (string); DECLARE_IMAGE_INSTANTIATOR_FORMAT (formatted_string); DECLARE_IMAGE_INSTANTIATOR_FORMAT (inherit); +DECLARE_IMAGE_INSTANTIATOR_FORMAT (layout); #ifdef HAVE_JPEG DECLARE_IMAGE_INSTANTIATOR_FORMAT (jpeg); #endif @@ -78,9 +79,6 @@ #endif DEFINE_DEVICE_IIFORMAT (mswindows, button); DEFINE_DEVICE_IIFORMAT (mswindows, edit_field); -#if 0 -DEFINE_DEVICE_IIFORMAT (mswindows, group); -#endif DEFINE_DEVICE_IIFORMAT (mswindows, subwindow); DEFINE_DEVICE_IIFORMAT (mswindows, widget); DEFINE_DEVICE_IIFORMAT (mswindows, label); @@ -101,13 +99,13 @@ static void mswindows_initialize_dibitmap_image_instance (struct Lisp_Image_Instance *ii, - enum image_instance_type type); + int slices, + enum image_instance_type type); static void mswindows_initialize_image_instance_mask (struct Lisp_Image_Instance* image, struct frame* f); COLORREF mswindows_string_to_color (CONST char *name); -void check_valid_item_list_1 (Lisp_Object items); #define BPLINE(width) ((int)(~3UL & (unsigned long)((width) +3))) @@ -293,6 +291,7 @@ int dest_mask, void *bmp_data, int bmp_bits, + int slices, Lisp_Object instantiator, int x_hot, int y_hot, int create_mask) @@ -334,12 +333,14 @@ /* copy in the actual bitmap */ memcpy (bmp_buf, bmp_data, bmp_bits); - mswindows_initialize_dibitmap_image_instance (ii, type); + mswindows_initialize_dibitmap_image_instance (ii, slices, type); IMAGE_INSTANCE_PIXMAP_FILENAME (ii) = find_keyword_in_vector (instantiator, Q_file); + /* Fixup a set of bitmaps. */ IMAGE_INSTANCE_MSWINDOWS_BITMAP (ii) = bitmap; + IMAGE_INSTANCE_MSWINDOWS_MASK (ii) = NULL; IMAGE_INSTANCE_PIXMAP_WIDTH (ii) = bmp_info->bmiHeader.biWidth; IMAGE_INSTANCE_PIXMAP_HEIGHT (ii) = bmp_info->bmiHeader.biHeight; @@ -359,8 +360,36 @@ } static void +image_instance_add_dibitmap (struct Lisp_Image_Instance *ii, + BITMAPINFO *bmp_info, + void *bmp_data, + int bmp_bits, + int slice, + Lisp_Object instantiator) +{ + Lisp_Object device = IMAGE_INSTANCE_DEVICE (ii); + struct device *d = XDEVICE (device); + struct frame *f = XFRAME (DEVICE_SELECTED_FRAME (d)); + void* bmp_buf=0; + HDC hdc = FRAME_MSWINDOWS_CDC (f); + HBITMAP bitmap = CreateDIBSection (hdc, + bmp_info, + DIB_RGB_COLORS, + &bmp_buf, + 0,0); + + if (!bitmap || !bmp_buf) + signal_simple_error ("Unable to create bitmap", instantiator); + + /* copy in the actual bitmap */ + memcpy (bmp_buf, bmp_data, bmp_bits); + IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE (ii, slice) = bitmap; +} + +static void mswindows_init_image_instance_from_eimage (struct Lisp_Image_Instance *ii, int width, int height, + int slices, unsigned char *eimage, int dest_mask, Lisp_Object instantiator, @@ -371,6 +400,7 @@ unsigned char* bmp_data; int bmp_bits; COLORREF bkcolor; + int slice; if (!DEVICE_MSWINDOWS_P (XDEVICE (device))) signal_simple_error ("Not an mswindows device", device); @@ -380,21 +410,29 @@ bkcolor = COLOR_INSTANCE_MSWINDOWS_COLOR (XCOLOR_INSTANCE (FACE_BACKGROUND (Vdefault_face, domain))); - /* build a bitmap from the eimage */ - if (!(bmp_info=convert_EImage_to_DIBitmap (device, width, height, eimage, - &bmp_bits, &bmp_data))) + for (slice = 0; slice < slices; slice++) { - signal_simple_error ("EImage to DIBitmap conversion failed", - instantiator); + /* build a bitmap from the eimage */ + if (!(bmp_info=convert_EImage_to_DIBitmap (device, width, height, + eimage + (width * height * 3 * slice), + &bmp_bits, &bmp_data))) + { + signal_simple_error ("EImage to DIBitmap conversion failed", + instantiator); + } + + /* Now create the pixmap and set up the image instance */ + if (slice == 0) + init_image_instance_from_dibitmap (ii, bmp_info, dest_mask, + bmp_data, bmp_bits, slices, instantiator, + 0, 0, 0); + else + image_instance_add_dibitmap (ii, bmp_info, bmp_data, bmp_bits, slice, + instantiator); + + xfree (bmp_info); + xfree (bmp_data); } - - /* Now create the pixmap and set up the image instance */ - init_image_instance_from_dibitmap (ii, bmp_info, dest_mask, - bmp_data, bmp_bits, instantiator, - 0, 0, 0); - - xfree (bmp_info); - xfree (bmp_data); } static void set_mono_pixel ( unsigned char* bits, @@ -923,7 +961,7 @@ /* Now create the pixmap and set up the image instance */ init_image_instance_from_dibitmap (ii, bmp_info, dest_mask, - bmp_data, bmp_bits, instantiator, + bmp_data, bmp_bits, 1, instantiator, x_hot, y_hot, transp); xfree (bmp_info); @@ -986,7 +1024,7 @@ /* Now create the pixmap and set up the image instance */ init_image_instance_from_dibitmap (ii, bmp_info, dest_mask, - bmp_data, bmp_bits, instantiator, + bmp_data, bmp_bits, 1, instantiator, 0, 0, 0); } @@ -1241,7 +1279,7 @@ if (hinst) FreeLibrary (hinst); - mswindows_initialize_dibitmap_image_instance (ii, iitype); + mswindows_initialize_dibitmap_image_instance (ii, 1, iitype); IMAGE_INSTANCE_PIXMAP_FILENAME (ii) = file; IMAGE_INSTANCE_PIXMAP_WIDTH (ii) = @@ -1723,7 +1761,7 @@ IMAGE_MONO_PIXMAP_MASK | IMAGE_COLOR_PIXMAP_MASK | IMAGE_POINTER_MASK); - mswindows_initialize_dibitmap_image_instance (ii, type); + mswindows_initialize_dibitmap_image_instance (ii, 1, type); IMAGE_INSTANCE_PIXMAP_FILENAME (ii) = find_keyword_in_vector (instantiator, Q_file); @@ -1984,6 +2022,10 @@ } } +#ifdef DEBUG_WIDGETS +extern int debug_widget_instances; +#endif + static void mswindows_finalize_image_instance (struct Lisp_Image_Instance *p) { @@ -1993,15 +2035,34 @@ || IMAGE_INSTANCE_TYPE (p) == IMAGE_SUBWINDOW) { +#ifdef DEBUG_WIDGETS + debug_widget_instances--; + stderr_out ("widget destroyed, %d left\n", debug_widget_instances); +#endif if (IMAGE_INSTANCE_SUBWINDOW_ID (p)) - DestroyWindow (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p)); - IMAGE_INSTANCE_SUBWINDOW_ID (p) = 0; + { + DestroyWindow (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p)); + DestroyWindow (IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (p)); + IMAGE_INSTANCE_SUBWINDOW_ID (p) = 0; + } } else if (p->data) { - if (IMAGE_INSTANCE_MSWINDOWS_BITMAP (p)) - DeleteObject (IMAGE_INSTANCE_MSWINDOWS_BITMAP (p)); - IMAGE_INSTANCE_MSWINDOWS_BITMAP (p) = 0; + int i; + if (IMAGE_INSTANCE_PIXMAP_TIMEOUT (p)) + disable_glyph_animated_timeout (IMAGE_INSTANCE_PIXMAP_TIMEOUT (p)); + + if (IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES (p)) + { + for (i = 0; i < IMAGE_INSTANCE_PIXMAP_MAXSLICE (p); i++) + { + if (IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE (p, i)) + DeleteObject (IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE (p, i)); + IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE (p, i) = 0; + } + xfree (IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES (p)); + IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES (p) = 0; + } if (IMAGE_INSTANCE_MSWINDOWS_MASK (p)) DeleteObject (IMAGE_INSTANCE_MSWINDOWS_MASK (p)); IMAGE_INSTANCE_MSWINDOWS_MASK (p) = 0; @@ -2029,31 +2090,46 @@ { if (IMAGE_INSTANCE_SUBWINDOW_ID (p)) { - SetWindowPos (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p), + SetWindowPos (IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (p), NULL, 0, 0, 0, 0, - SWP_HIDEWINDOW | SWP_NOMOVE | SWP_NOSIZE - | SWP_NOCOPYBITS | SWP_NOSENDCHANGING); + SWP_HIDEWINDOW | SWP_NOMOVE | SWP_NOSIZE + | SWP_NOSENDCHANGING); } } /* map the subwindow. This is used by redisplay via redisplay_output_subwindow */ static void -mswindows_map_subwindow (struct Lisp_Image_Instance *p, int x, int y) +mswindows_map_subwindow (struct Lisp_Image_Instance *p, int x, int y, + struct display_glyph_area* dga) { - /* ShowWindow (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p), SW_SHOW);*/ - SetWindowPos (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p), + /* move the window before mapping it ... */ + SetWindowPos (IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (p), + NULL, + x, y, dga->width, dga->height, + SWP_NOZORDER + | SWP_NOCOPYBITS | SWP_NOSENDCHANGING); + /* ... adjust the child ... */ + SetWindowPos (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p), NULL, - x, y, 0, 0, - SWP_NOZORDER | SWP_SHOWWINDOW | SWP_NOSIZE + -dga->xoffset, -dga->yoffset, 0, 0, + SWP_NOZORDER | SWP_NOSIZE | SWP_NOCOPYBITS | SWP_NOSENDCHANGING); + /* ... now map it - we are not allowed to move it at the same time. */ + SetWindowPos (IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (p), + NULL, + 0, 0, 0, 0, + SWP_NOZORDER | SWP_NOSIZE | SWP_NOMOVE + | SWP_SHOWWINDOW | SWP_NOCOPYBITS + | SWP_NOSENDCHANGING); } /* resize the subwindow instance */ static void mswindows_resize_subwindow (struct Lisp_Image_Instance* ii, int w, int h) { + /* Set the size of the control .... */ SetWindowPos (WIDGET_INSTANCE_MSWINDOWS_HANDLE (ii), NULL, 0, 0, w, h, @@ -2071,13 +2147,23 @@ /* buttons checked or otherwise */ if ( EQ (IMAGE_INSTANCE_WIDGET_TYPE (p), Qbutton)) { - if (gui_item_selected_p (IMAGE_INSTANCE_WIDGET_SINGLE_ITEM (p))) + if (gui_item_selected_p (IMAGE_INSTANCE_WIDGET_ITEM (p))) SendMessage (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p), BM_SETCHECK, (WPARAM)BST_CHECKED, 0); else SendMessage (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p), BM_SETCHECK, (WPARAM)BST_UNCHECKED, 0); } + + /* set the widget font from the widget face */ + SendMessage (WIDGET_INSTANCE_MSWINDOWS_HANDLE (p), + WM_SETFONT, + (WPARAM)FONT_INSTANCE_MSWINDOWS_HFONT + (XFONT_INSTANCE (widget_face_font_info + (IMAGE_INSTANCE_SUBWINDOW_FRAME (p), + IMAGE_INSTANCE_WIDGET_FACE (p), + 0, 0))), + MAKELPARAM (TRUE, 0)); } } @@ -2101,7 +2187,7 @@ static int mswindows_register_widget_instance (Lisp_Object instance, Lisp_Object domain) { - return mswindows_register_gui_item (XIMAGE_INSTANCE_WIDGET_SINGLE_ITEM (instance), + return mswindows_register_gui_item (XIMAGE_INSTANCE_WIDGET_ITEM (instance), domain); } @@ -2122,6 +2208,26 @@ /* have to set the type this late in case there is no device instantiation for a widget */ IMAGE_INSTANCE_TYPE (ii) = IMAGE_SUBWINDOW; + /* Allocate space for the clip window */ + ii->data = xnew_and_zero (struct mswindows_subwindow_data); + + if ((IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (ii) + = CreateWindowEx( + 0, /* EX flags */ + XEMACS_CONTROL_CLASS, + 0, /* text */ + WS_CLIPCHILDREN | WS_CLIPSIBLINGS | WS_CHILD, + 0, /* starting x position */ + 0, /* starting y position */ + IMAGE_INSTANCE_WIDGET_WIDTH (ii), + IMAGE_INSTANCE_WIDGET_HEIGHT (ii), + /* parent window */ + FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), + NULL, /* No menu */ + NULL, /* must be null for this class */ + NULL)) == NULL) + signal_simple_error ("window creation failed with code", + make_int (GetLastError())); wnd = CreateWindow( "STATIC", "", @@ -2130,7 +2236,7 @@ 0, /* starting y position */ IMAGE_INSTANCE_WIDGET_WIDTH (ii), IMAGE_INSTANCE_WIDGET_HEIGHT (ii), - FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), /* parent window */ + IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (ii), 0, (HINSTANCE) GetWindowLong (FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), @@ -2185,6 +2291,7 @@ static void mswindows_initialize_dibitmap_image_instance (struct Lisp_Image_Instance *ii, + int slices, enum image_instance_type type) { ii->data = xnew_and_zero (struct mswindows_image_instance_data); @@ -2195,9 +2302,14 @@ IMAGE_INSTANCE_PIXMAP_HOTSPOT_Y (ii) = Qnil; IMAGE_INSTANCE_PIXMAP_FG (ii) = Qnil; IMAGE_INSTANCE_PIXMAP_BG (ii) = Qnil; + IMAGE_INSTANCE_PIXMAP_MAXSLICE (ii) = slices; + IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES (ii) = + xnew_array_and_zero (HBITMAP, slices); } +#ifdef HAVE_WIDGETS + /************************************************************************/ /* widgets */ /************************************************************************/ @@ -2207,11 +2319,8 @@ int dest_mask, Lisp_Object domain, CONST char* class, int flags, int exflags) { + /* this function can call lisp */ struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); -#if 0 - struct Lisp_Image_Instance *groupii = 0; - Lisp_Object group = find_keyword_in_vector (instantiator, Q_group); -#endif Lisp_Object device = IMAGE_INSTANCE_DEVICE (ii), style; struct device* d = XDEVICE (device); Lisp_Object frame = FW_FRAME (domain); @@ -2223,17 +2332,7 @@ if (!DEVICE_MSWINDOWS_P (d)) signal_simple_error ("Not an mswindows device", device); -#if 0 - /* if the user specified another glyph as a group pick up the - instance in our domain. */ - if (!NILP (group)) - { - if (SYMBOLP (group)) - group = XSYMBOL (group)->value; - group = glyph_image_instance (group, domain, ERROR_ME, 1); - groupii = XIMAGE_INSTANCE (group); - } -#endif + if (!gui_item_active_p (gui)) flags |= WS_DISABLED; @@ -2249,22 +2348,46 @@ if (!NILP (IMAGE_INSTANCE_WIDGET_TEXT (ii))) GET_C_STRING_OS_DATA_ALLOCA (IMAGE_INSTANCE_WIDGET_TEXT (ii), nm); - wnd = CreateWindowEx( - exflags /* | WS_EX_NOPARENTNOTIFY*/, - class, - nm, - flags | WS_CHILD, - 0, /* starting x position */ - 0, /* starting y position */ - IMAGE_INSTANCE_WIDGET_WIDTH (ii), - IMAGE_INSTANCE_WIDGET_HEIGHT (ii), - /* parent window */ - FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), - (HMENU)id, /* No menu */ - (HINSTANCE) - GetWindowLong (FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), - GWL_HINSTANCE), - NULL); + /* allocate space for the clip window and then allocate the clip window */ + ii->data = xnew_and_zero (struct mswindows_subwindow_data); + + if ((IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (ii) + = CreateWindowEx( + 0, /* EX flags */ + XEMACS_CONTROL_CLASS, + 0, /* text */ + WS_CLIPCHILDREN | WS_CLIPSIBLINGS | WS_CHILD, + 0, /* starting x position */ + 0, /* starting y position */ + IMAGE_INSTANCE_WIDGET_WIDTH (ii), + IMAGE_INSTANCE_WIDGET_HEIGHT (ii), + /* parent window */ + FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), + (HMENU)id, /* No menu */ + NULL, /* must be null for this class */ + NULL)) == NULL) + signal_simple_error ("window creation failed with code", + make_int (GetLastError())); + + if ((wnd = CreateWindowEx( + exflags /* | WS_EX_NOPARENTNOTIFY*/, + class, + nm, + flags | WS_CHILD | WS_VISIBLE, + 0, /* starting x position */ + 0, /* starting y position */ + IMAGE_INSTANCE_WIDGET_WIDTH (ii), + IMAGE_INSTANCE_WIDGET_HEIGHT (ii), + /* parent window */ + IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (ii), + (HMENU)id, /* No menu */ + (HINSTANCE) + GetWindowLong + (FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), + GWL_HINSTANCE), + NULL)) == NULL) + signal_simple_error ("window creation failed with code", + make_int (GetLastError())); IMAGE_INSTANCE_SUBWINDOW_ID (ii) = wnd; SetWindowLong (wnd, GWL_USERDATA, (LONG)LISP_TO_VOID(image_instance)); @@ -2289,6 +2412,7 @@ Lisp_Object pointer_fg, Lisp_Object pointer_bg, int dest_mask, Lisp_Object domain) { + /* this function can call lisp */ struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); HWND wnd; int flags = BS_NOTIFY; @@ -2392,7 +2516,7 @@ /* instantiate a tree view widget */ static HTREEITEM add_tree_item (Lisp_Object image_instance, - HWND wnd, HTREEITEM parent, Lisp_Object entry, + HWND wnd, HTREEITEM parent, Lisp_Object item, int children, Lisp_Object domain) { TV_INSERTSTRUCT tvitem; @@ -2403,39 +2527,21 @@ tvitem.item.mask = TVIF_TEXT | TVIF_CHILDREN; tvitem.item.cChildren = children; - if (VECTORP (entry)) + if (GUI_ITEMP (item)) { - /* we always maintain the real gui item at the head of the - list. We have to put them in the list in the first place - because the whole model assumes that the glyph instances have - references to all the associated data. If we didn't do this - GC would bite us badly. */ - Lisp_Object gui = gui_parse_item_keywords_no_errors (entry); - if (CONSP (XIMAGE_INSTANCE_WIDGET_ITEM (image_instance))) - { - Lisp_Object rest = - Fcons (gui, XCDR (XIMAGE_INSTANCE_WIDGET_ITEM (image_instance))); - Fsetcdr (XIMAGE_INSTANCE_WIDGET_ITEM (image_instance), rest); - } - else - { - XIMAGE_INSTANCE_WIDGET_ITEM (image_instance) = - Fcons (XIMAGE_INSTANCE_WIDGET_ITEM (image_instance), gui); - } - - tvitem.item.lParam = mswindows_register_gui_item (gui, domain); + tvitem.item.lParam = mswindows_register_gui_item (item, domain); tvitem.item.mask |= TVIF_PARAM; - GET_C_STRING_OS_DATA_ALLOCA (XGUI_ITEM (gui)->name, + GET_C_STRING_OS_DATA_ALLOCA (XGUI_ITEM (item)->name, tvitem.item.pszText); } else - GET_C_STRING_OS_DATA_ALLOCA (entry, tvitem.item.pszText); + GET_C_STRING_OS_DATA_ALLOCA (item, tvitem.item.pszText); tvitem.item.cchTextMax = strlen (tvitem.item.pszText); if ((ret = (HTREEITEM)SendMessage (wnd, TVM_INSERTITEM, 0, (LPARAM)&tvitem)) == 0) - signal_simple_error ("error adding tree view entry", entry); + signal_simple_error ("error adding tree view entry", item); return ret; } @@ -2476,12 +2582,13 @@ wnd = WIDGET_INSTANCE_MSWINDOWS_HANDLE (ii); /* define a root */ - parent = add_tree_item (image_instance, - wnd, NULL, IMAGE_INSTANCE_WIDGET_TEXT (ii), TRUE, - domain); + parent = add_tree_item (image_instance, wnd, NULL, + XCAR (IMAGE_INSTANCE_WIDGET_ITEMS (ii)), + TRUE, domain); /* recursively add items to the tree view */ - LIST_LOOP (rest, Fplist_get (IMAGE_INSTANCE_WIDGET_PROPS (ii), Q_items, Qnil)) + /* add items to the tab */ + LIST_LOOP (rest, XCDR (IMAGE_INSTANCE_WIDGET_ITEMS (ii))) { if (LISTP (XCAR (rest))) add_tree_item_list (image_instance, wnd, parent, XCAR (rest), domain); @@ -2492,46 +2599,31 @@ /* instantiate a tab control */ static TC_ITEM* add_tab_item (Lisp_Object image_instance, - HWND wnd, Lisp_Object entry, + HWND wnd, Lisp_Object item, Lisp_Object domain, int index) { TC_ITEM tvitem, *ret; tvitem.mask = TCIF_TEXT; - if (VECTORP (entry)) + if (GUI_ITEMP (item)) { - /* we always maintain the real gui item at the head of the - list. We have to put them in the list in the first place - because the whole model assumes that the glyph instances have - references to all the associated data. If we didn't do this - GC would bite us badly. */ - Lisp_Object gui = gui_parse_item_keywords_no_errors (entry); - if (CONSP (XIMAGE_INSTANCE_WIDGET_ITEM (image_instance))) - { - Lisp_Object rest = - Fcons (gui, XCDR (XIMAGE_INSTANCE_WIDGET_ITEM (image_instance))); - Fsetcdr (XIMAGE_INSTANCE_WIDGET_ITEM (image_instance), rest); - } - else - { - XIMAGE_INSTANCE_WIDGET_ITEM (image_instance) = - Fcons (XIMAGE_INSTANCE_WIDGET_ITEM (image_instance), gui); - } - - tvitem.lParam = mswindows_register_gui_item (gui, domain); + tvitem.lParam = mswindows_register_gui_item (item, domain); tvitem.mask |= TCIF_PARAM; - GET_C_STRING_OS_DATA_ALLOCA (XGUI_ITEM (gui)->name, + GET_C_STRING_OS_DATA_ALLOCA (XGUI_ITEM (item)->name, tvitem.pszText); } else - GET_C_STRING_OS_DATA_ALLOCA (entry, tvitem.pszText); + { + CHECK_STRING (item); + GET_C_STRING_OS_DATA_ALLOCA (item, tvitem.pszText); + } tvitem.cchTextMax = strlen (tvitem.pszText); if ((ret = (TC_ITEM*)SendMessage (wnd, TCM_INSERTITEM, index, (LPARAM)&tvitem)) < 0) - signal_simple_error ("error adding tab entry", entry); + signal_simple_error ("error adding tab entry", item); return ret; } @@ -2553,7 +2645,7 @@ wnd = WIDGET_INSTANCE_MSWINDOWS_HANDLE (ii); /* add items to the tab */ - LIST_LOOP (rest, Fplist_get (IMAGE_INSTANCE_WIDGET_PROPS (ii), Q_items, Qnil)) + LIST_LOOP (rest, XCDR (IMAGE_INSTANCE_WIDGET_ITEMS (ii))) { add_tab_item (image_instance, wnd, XCAR (rest), domain, index); index++; @@ -2577,8 +2669,12 @@ /* delete the pre-existing items */ SendMessage (wnd, TCM_DELETEALLITEMS, 0, 0); + IMAGE_INSTANCE_WIDGET_ITEMS (ii) = + Fcons (XCAR (IMAGE_INSTANCE_WIDGET_ITEMS (ii)), + parse_gui_item_tree_children (val)); + /* add items to the tab */ - LIST_LOOP (rest, val) + LIST_LOOP (rest, XCDR (IMAGE_INSTANCE_WIDGET_ITEMS (ii))) { add_tab_item (image_instance, wnd, XCAR (rest), IMAGE_INSTANCE_SUBWINDOW_FRAME (ii), index); @@ -2601,20 +2697,6 @@ 0, WS_EX_STATICEDGE); } -#if 0 -/* instantiate a static control possible for putting other things in */ -static void -mswindows_group_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, - Lisp_Object pointer_fg, Lisp_Object pointer_bg, - int dest_mask, Lisp_Object domain) -{ - mswindows_widget_instantiate (image_instance, instantiator, pointer_fg, - pointer_bg, dest_mask, domain, "BUTTON", - WS_GROUP | BS_GROUPBOX | WS_BORDER, - WS_EX_CLIENTEDGE ); -} -#endif - /* instantiate a scrollbar control */ static void mswindows_scrollbar_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, @@ -2636,6 +2718,10 @@ struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); HANDLE wnd; Lisp_Object rest; + Lisp_Object data = Fplist_get (find_keyword_in_vector (instantiator, Q_properties), + Q_items, Qnil); + int len; + GET_LIST_LENGTH (data, len); /* Maybe ought to generalise this more but it may be very windows specific. In windows the window height of a combo box is the @@ -2643,6 +2729,9 @@ before creating the window and then reset it to a single line after the window is created so that redisplay does the right thing. */ + widget_instantiate_1 (image_instance, instantiator, pointer_fg, + pointer_bg, dest_mask, domain, len + 1, 0, 0); + mswindows_widget_instantiate (image_instance, instantiator, pointer_fg, pointer_bg, dest_mask, domain, "COMBOBOX", WS_BORDER | WS_TABSTOP | CBS_DROPDOWN @@ -2754,6 +2843,28 @@ return Qunbound; } +LRESULT WINAPI +mswindows_control_wnd_proc (HWND hwnd, UINT message, + WPARAM wParam, LPARAM lParam) +{ + switch (message) + { + case WM_NOTIFY: + case WM_COMMAND: + case WM_CTLCOLORBTN: + case WM_CTLCOLORLISTBOX: + case WM_CTLCOLOREDIT: + case WM_CTLCOLORSTATIC: + case WM_CTLCOLORSCROLLBAR: + + return mswindows_wnd_proc (GetParent (hwnd), message, wParam, lParam); + default: + return DefWindowProc (hwnd, message, wParam, lParam); + } +} + +#endif /* HAVE_WIDGETS */ + /************************************************************************/ /* initialization */ @@ -2788,6 +2899,7 @@ { IIFORMAT_VALID_CONSOLE (mswindows, nothing); IIFORMAT_VALID_CONSOLE (mswindows, string); + IIFORMAT_VALID_CONSOLE (mswindows, layout); IIFORMAT_VALID_CONSOLE (mswindows, formatted_string); IIFORMAT_VALID_CONSOLE (mswindows, inherit); /* image-instantiator types */ @@ -2813,6 +2925,7 @@ #ifdef HAVE_GIF IIFORMAT_VALID_CONSOLE (mswindows, gif); #endif +#ifdef HAVE_WIDGETS /* button widget */ INITIALIZE_DEVICE_IIFORMAT (mswindows, button); IIFORMAT_HAS_DEVMETHOD (mswindows, button, property); @@ -2827,10 +2940,7 @@ INITIALIZE_DEVICE_IIFORMAT (mswindows, widget); IIFORMAT_HAS_DEVMETHOD (mswindows, widget, property); IIFORMAT_HAS_DEVMETHOD (mswindows, widget, set_property); -#if 0 - INITIALIZE_DEVICE_IIFORMAT (mswindows, group); - IIFORMAT_HAS_DEVMETHOD (mswindows, group, instantiate); -#endif + /* label */ INITIALIZE_DEVICE_IIFORMAT (mswindows, label); IIFORMAT_HAS_DEVMETHOD (mswindows, label, instantiate); @@ -2858,7 +2968,7 @@ INITIALIZE_DEVICE_IIFORMAT (mswindows, tab_control); IIFORMAT_HAS_DEVMETHOD (mswindows, tab_control, instantiate); IIFORMAT_HAS_DEVMETHOD (mswindows, tab_control, set_property); - +#endif /* windows bitmap format */ INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (bmp, "bmp"); IIFORMAT_HAS_METHOD (bmp, validate); diff -r 28d9c139be4c -r 11054d720c21 src/glyphs-msw.h --- a/src/glyphs-msw.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/glyphs-msw.h Mon Aug 13 11:26:11 2007 +0200 @@ -34,8 +34,7 @@ struct mswindows_image_instance_data { - HBITMAP bitmap; - HBITMAP mask; + HBITMAP* bitmaps; HICON icon; }; @@ -43,14 +42,22 @@ ((struct mswindows_image_instance_data *) (i)->data) #define IMAGE_INSTANCE_MSWINDOWS_BITMAP(i) \ - (MSWINDOWS_IMAGE_INSTANCE_DATA (i)->bitmap) + (MSWINDOWS_IMAGE_INSTANCE_DATA (i)->bitmaps[0]) +#define IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE(i,slice) \ + (MSWINDOWS_IMAGE_INSTANCE_DATA (i)->bitmaps[slice]) +#define IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES(i) \ + (MSWINDOWS_IMAGE_INSTANCE_DATA (i)->bitmaps) #define IMAGE_INSTANCE_MSWINDOWS_MASK(i) \ - (MSWINDOWS_IMAGE_INSTANCE_DATA (i)->mask) + (HBITMAP)(IMAGE_INSTANCE_PIXMAP_MASK (i)) #define IMAGE_INSTANCE_MSWINDOWS_ICON(i) \ (MSWINDOWS_IMAGE_INSTANCE_DATA (i)->icon) #define XIMAGE_INSTANCE_MSWINDOWS_BITMAP(i) \ IMAGE_INSTANCE_MSWINDOWS_BITMAP (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE(i,slice) \ + IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE (XIMAGE_INSTANCE (i,slice)) +#define XIMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES(i) \ + IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICES (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_MSWINDOWS_MASK(i) \ IMAGE_INSTANCE_MSWINDOWS_MASK (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_MSWINDOWS_ICON(i) \ @@ -78,5 +85,19 @@ #define XWIDGET_INSTANCE_MSWINDOWS_HANDLE(i) \ WIDGET_INSTANCE_MSWINDOWS_HANDLE (XIMAGE_INSTANCE (i)) +struct mswindows_subwindow_data +{ + HWND clip_window; +}; + +#define MSWINDOWS_SUBWINDOW_DATA(i) \ +((struct mswindows_subwindow_data *) (i)->data) + +#define IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW(i) \ + (MSWINDOWS_SUBWINDOW_DATA (i)->clip_window) + +#define XIMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW(i) \ + IMAGE_INSTANCE_MSWINDOWS_CLIPWINDOW (XIMAGE_INSTANCE (i)) + #endif /* HAVE_MS_WINDOWS */ #endif /* _XEMACS_GLYPHS_MSW_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/glyphs-widget.c --- a/src/glyphs-widget.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/glyphs-widget.c Mon Aug 13 11:26:11 2007 +0200 @@ -1,5 +1,5 @@ /* Widget-specific glyph objects. - Copyright (C) 1998 Andy Piper + Copyright (C) 1998, 1999 Andy Piper. This file is part of XEmacs. @@ -45,10 +45,6 @@ DEFINE_IMAGE_INSTANTIATOR_FORMAT (scrollbar); Lisp_Object Qscrollbar; DEFINE_IMAGE_INSTANTIATOR_FORMAT (widget); -#if 0 -DEFINE_IMAGE_INSTANTIATOR_FORMAT (group); -Lisp_Object Qgroup; -#endif DEFINE_IMAGE_INSTANTIATOR_FORMAT (label); Lisp_Object Qlabel; DEFINE_IMAGE_INSTANTIATOR_FORMAT (progress_gauge); @@ -57,13 +53,20 @@ Lisp_Object Qtree_view; DEFINE_IMAGE_INSTANTIATOR_FORMAT (tab_control); Lisp_Object Qtab_control; +DEFINE_IMAGE_INSTANTIATOR_FORMAT (layout); +Lisp_Object Qlayout; Lisp_Object Q_descriptor, Q_height, Q_width, Q_properties, Q_items; -Lisp_Object Q_image, Q_text, Q_percent; +Lisp_Object Q_image, Q_text, Q_percent, Q_orientation, Q_justify, Q_border; +Lisp_Object Qetched_in, Qetched_out, Qbevel_in, Qbevel_out; -#define WIDGET_BORDER_HEIGHT 2 +#define WIDGET_BORDER_HEIGHT 4 #define WIDGET_BORDER_WIDTH 4 +#ifdef DEBUG_WIDGETS +int debug_widget_instances; +#endif + /* TODO: - more complex controls. - tooltips for controls. @@ -96,7 +99,7 @@ int ch=0, cw=0; widget_face_font_info (domain, face, &ch, &cw); if (height) - *height = th * (ch + 2 * WIDGET_BORDER_HEIGHT); + *height = th * ch + 2 * WIDGET_BORDER_HEIGHT; if (width) *width = tw * cw + 2 * WIDGET_BORDER_WIDTH; } @@ -108,7 +111,7 @@ } static void -check_valid_glyph_or_image (Lisp_Object data) +check_valid_glyph_or_instantiator (Lisp_Object data) { Lisp_Object glyph = data; if (SYMBOLP (data)) @@ -116,11 +119,36 @@ if (IMAGE_INSTANCEP (glyph)) CHECK_IMAGE_INSTANCE (glyph); - else if (!CONSP (glyph)) + else if (!CONSP (glyph) && !VECTORP (glyph)) CHECK_BUFFER_GLYPH (glyph); } static void +check_valid_orientation (Lisp_Object data) +{ + if (!EQ (data, Qhorizontal) + && + !EQ (data, Qvertical)) + signal_simple_error ("unknown orientation for layout", data); +} + +static void +check_valid_justification (Lisp_Object data) +{ + if (!EQ (data, Qleft) && !EQ (data, Qright) && !EQ (data, Qcenter)) + signal_simple_error ("unknown justification for layout", data); +} + +static void +check_valid_border (Lisp_Object data) +{ + if (!EQ (data, Qt) && !EQ (data, Qetched_in) && !EQ (data, Qetched_out) + && !EQ (data, Qbevel_in) && !EQ (data, Qbevel_out) + && !GLYPHP (data) && !VECTORP (data)) + signal_simple_error ("unknown border style for layout", data); +} + +static void check_valid_anything (Lisp_Object data) { } @@ -179,6 +207,58 @@ check_valid_item_list_1 (items); } +static void +check_valid_glyph_or_instantiator_list (Lisp_Object data) +{ + Lisp_Object rest; + + CHECK_LIST (data); + EXTERNAL_LIST_LOOP (rest, data) + { + check_valid_glyph_or_instantiator (XCAR (rest)); + } +} + +static Lisp_Object +glyph_instantiator_to_glyph (Lisp_Object sym) +{ + /* This function calls lisp. */ + Lisp_Object glyph = sym; + struct gcpro gcpro1; + + GCPRO1 (glyph); + /* if we have a symbol get at the actual data */ + if (SYMBOLP (glyph)) + glyph = XSYMBOL (glyph)->value; + + if (CONSP (glyph)) + glyph = Feval (glyph); + + /* Be really helpful to the user. */ + if (VECTORP (glyph)) + { + glyph = call1 (intern ("make-glyph"), glyph); + } + + /* substitute the new glyph */ + RETURN_UNGCPRO (glyph); +} + +static void +substitute_keyword_value (Lisp_Object inst, Lisp_Object key, Lisp_Object val) +{ + int i; + /* substitute the new glyph */ + for (i = 0; i < XVECTOR_LENGTH (inst); i++) + { + if (EQ (key, XVECTOR_DATA (inst)[i])) + { + XVECTOR_DATA (inst)[i+1] = val; + break; + } + } +} + /* wire widget property invocations to specific widgets ... The problem we are solving here is that when instantiators get converted to instances they lose some type information (they just become @@ -289,25 +369,9 @@ same reasons we normalize file to data. */ if (!NILP (glyph)) { - int i; - struct gcpro gcpro1; - if (SYMBOLP (glyph)) - glyph = XSYMBOL (glyph)->value; - GCPRO1 (glyph); + substitute_keyword_value (inst, Q_image, glyph_instantiator_to_glyph (glyph)); + } - if (CONSP (glyph)) - glyph = Feval (glyph); - /* substitute the new glyph */ - for (i = 0; i < XVECTOR_LENGTH (inst); i++) - { - if (EQ (Q_image, XVECTOR_DATA (inst)[i])) - { - XVECTOR_DATA (inst)[i+1] = glyph; - break; - } - } - UNGCPRO; - } return inst; } @@ -318,7 +382,7 @@ IMAGE_INSTANCE_WIDGET_TYPE (ii) = type; IMAGE_INSTANCE_WIDGET_PROPS (ii) = Qnil; IMAGE_INSTANCE_WIDGET_FACE (ii) = Vwidget_face; - IMAGE_INSTANCE_WIDGET_ITEM (ii) = allocate_gui_item (); + IMAGE_INSTANCE_WIDGET_ITEMS (ii) = allocate_gui_item (); } /* Instantiate a button widget. Unfortunately instantiated widgets are @@ -327,7 +391,7 @@ want to display it in and BitBlt it. So image instances can have a many-to-one relationship with things you see, whereas widgets can only be one-to-one (i.e. per frame) */ -static void +void widget_instantiate_1 (Lisp_Object image_instance, Lisp_Object instantiator, Lisp_Object pointer_fg, Lisp_Object pointer_bg, int dest_mask, Lisp_Object domain, int default_textheight, @@ -341,6 +405,7 @@ Lisp_Object pixheight = find_keyword_in_vector (instantiator, Q_pixel_height); Lisp_Object desc = find_keyword_in_vector (instantiator, Q_descriptor); Lisp_Object glyph = find_keyword_in_vector (instantiator, Q_image); + Lisp_Object props = find_keyword_in_vector (instantiator, Q_properties); int pw=0, ph=0, tw=0, th=0; /* this just does pixel type sizing */ @@ -357,8 +422,7 @@ IMAGE_INSTANCE_WIDGET_FACE (ii) = Fget_face (face); /* data items for some widgets */ - IMAGE_INSTANCE_WIDGET_PROPS (ii) = - find_keyword_in_vector (instantiator, Q_properties); + IMAGE_INSTANCE_WIDGET_PROPS (ii) = props; /* retrieve the gui item information. This is easy if we have been provided with a vector, more difficult if we have just been given @@ -366,14 +430,24 @@ if (STRINGP (desc) || NILP (desc)) { /* big cheat - we rely on the fact that a gui item looks like an instantiator */ - IMAGE_INSTANCE_WIDGET_ITEM (ii) = + IMAGE_INSTANCE_WIDGET_ITEMS (ii) = gui_parse_item_keywords_no_errors (instantiator); IMAGE_INSTANCE_WIDGET_TEXT (ii) = desc; } else - IMAGE_INSTANCE_WIDGET_ITEM (ii) = + IMAGE_INSTANCE_WIDGET_ITEMS (ii) = gui_parse_item_keywords_no_errors (desc); + /* parse more gui items out of the properties */ + if (!NILP (props)) + { + Lisp_Object items = Fplist_get (props, Q_items, Qnil); + if (!NILP (items)) + IMAGE_INSTANCE_WIDGET_ITEMS (ii) = + Fcons (IMAGE_INSTANCE_WIDGET_ITEMS (ii), + parse_gui_item_tree_children (items)); + } + /* normalize size information */ if (!NILP (width)) tw = XINT (width); @@ -421,6 +495,12 @@ IMAGE_INSTANCE_SUBWINDOW_WIDTH (ii) = pw; IMAGE_INSTANCE_SUBWINDOW_HEIGHT (ii) = ph; +#ifdef DEBUG_WIDGETS + debug_widget_instances++; + stderr_out ("instantiated "); + debug_print (instantiator); + stderr_out ("%d widgets instantiated\n", debug_widget_instances); +#endif } static void @@ -432,11 +512,11 @@ pointer_bg, dest_mask, domain, 1, 0, 0); } -/* combo-box generic instantiation - get he heigh right */ +/* tree-view generic instantiation - get the height right */ static void -combo_box_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, - Lisp_Object pointer_fg, Lisp_Object pointer_bg, - int dest_mask, Lisp_Object domain) +tree_view_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, + Lisp_Object pointer_fg, Lisp_Object pointer_bg, + int dest_mask, Lisp_Object domain) { Lisp_Object data = Fplist_get (find_keyword_in_vector (instantiator, Q_properties), Q_items, Qnil); @@ -483,6 +563,209 @@ } +/***************************************************************************** + * widget layout * + *****************************************************************************/ +static int +layout_possible_dest_types (void) +{ + return IMAGE_LAYOUT_MASK; +} + +/* we need to convert things like glyphs to images, eval expressions + etc.*/ +static Lisp_Object +layout_normalize (Lisp_Object inst, Lisp_Object console_type) +{ + /* This function can call lisp */ + Lisp_Object items = find_keyword_in_vector (inst, Q_items); + Lisp_Object border = find_keyword_in_vector (inst, Q_border); + /* we need to eval glyph if its an expression, we do this for the + same reasons we normalize file to data. */ + if (!NILP (items)) + { + Lisp_Object rest; + LIST_LOOP (rest, items) + { + /* substitute the new glyph */ + Fsetcar (rest, glyph_instantiator_to_glyph (XCAR (rest))); + } + } + /* normalize the border spec. */ + if (VECTORP (border) || CONSP (border)) + { + substitute_keyword_value (inst, Q_border, glyph_instantiator_to_glyph (border)); + } + return inst; +} + +/* Instantiate a layout widget. */ +static void +layout_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, + Lisp_Object pointer_fg, Lisp_Object pointer_bg, + int dest_mask, Lisp_Object domain) +{ + struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); + Lisp_Object rest, device = IMAGE_INSTANCE_DEVICE (ii); + Lisp_Object frame = FW_FRAME (domain); + Lisp_Object items = find_keyword_in_vector (instantiator, Q_items); + Lisp_Object width = find_keyword_in_vector (instantiator, Q_pixel_width); + Lisp_Object height = find_keyword_in_vector (instantiator, Q_pixel_height); + Lisp_Object orient = find_keyword_in_vector (instantiator, Q_orientation); + Lisp_Object justify = find_keyword_in_vector (instantiator, Q_justify); + Lisp_Object border = find_keyword_in_vector (instantiator, Q_border); + Lisp_Object children = Qnil; + int pw = 0, ph = 0, x, y, maxph = 0, maxpw = 0, nitems = 0, + horiz_spacing, vert_spacing, ph_adjust = 0; + + if (NILP (frame)) + signal_simple_error ("No selected frame", device); + + if (!(dest_mask & IMAGE_LAYOUT_MASK)) + incompatible_image_types (instantiator, dest_mask, IMAGE_LAYOUT_MASK); + + if (NILP (orient)) + orient = Qvertical; + + if (EQ (border, Qt)) + border = Qetched_in; + + ii->data = 0; + IMAGE_INSTANCE_TYPE (ii) = IMAGE_LAYOUT; + IMAGE_INSTANCE_SUBWINDOW_ID (ii) = 0; + IMAGE_INSTANCE_SUBWINDOW_DISPLAYEDP (ii) = 0; + IMAGE_INSTANCE_SUBWINDOW_FRAME (ii) = frame; + IMAGE_INSTANCE_LAYOUT_BORDER (ii) = border; + + /* normalize size information */ + if (!NILP (width)) + pw = XINT (width); + if (!NILP (height)) + ph = XINT (height); + + /* flip through the items to work out how much stuff we have to display */ + LIST_LOOP (rest, items) + { + Lisp_Object glyph = XCAR (rest); + int gheight = glyph_height (glyph, Qnil, DEFAULT_INDEX, domain); + int gwidth = glyph_width (glyph, Qnil, DEFAULT_INDEX, domain); + nitems ++; + if (EQ (orient, Qhorizontal)) + { + maxph = max (maxph, gheight); + maxpw += gwidth; + } + else if (EQ (orient, Qvertical)) + { + maxpw = max (maxpw, gwidth); + maxph += gheight; + } + } + + /* work out spacing between items and bounds of the layout */ + if (!pw) + { + /* No user provided width so we just do default spacing. */ + horiz_spacing = WIDGET_BORDER_WIDTH * 2; + if (EQ (orient, Qhorizontal)) + pw = maxpw + (nitems + 1) * horiz_spacing; + else + pw = maxpw + 2 * horiz_spacing; + } + else if (pw < maxpw) + /* The user wants a smaller space than the largest item, so we + just provide default spacing and will let the output routines + clip.. */ + horiz_spacing = WIDGET_BORDER_WIDTH * 2; + else if (EQ (orient, Qhorizontal)) + /* We have a larger area to display in so distribute the space + evenly. */ + horiz_spacing = (pw - maxpw) / (nitems + 1); + else + horiz_spacing = (pw - maxpw) / 2; + + /* Do the border now so that we can adjust the layout. */ + if (GLYPHP (border)) + { + /* We are going to be sneaky here and add the border text as + just another child, the layout and output routines don't know + this and will just display at the offsets we prescribe. */ + Lisp_Object bglyph = glyph_image_instance (border, domain, ERROR_ME, 1); + + children = Fcons (bglyph, children); + XIMAGE_INSTANCE_XOFFSET (bglyph) = 10; /* Really, what should this be? */ + XIMAGE_INSTANCE_YOFFSET (bglyph) = 0; + + ph_adjust = (glyph_height (border, Qnil, DEFAULT_INDEX, domain) / 2); + IMAGE_INSTANCE_LAYOUT_BORDER (ii) = make_int (ph_adjust); + } + + /* Work out vertical spacings. */ + if (!ph) + { + vert_spacing = WIDGET_BORDER_HEIGHT * 2; + if (EQ (orient, Qvertical)) + ph = maxph + (nitems + 1) * vert_spacing + ph_adjust; + else + ph = maxph + 2 * vert_spacing + ph_adjust; + } + else if (ph < maxph) + vert_spacing = WIDGET_BORDER_HEIGHT * 2; + else if (EQ (orient, Qvertical)) + vert_spacing = (ph - (maxph + ph_adjust)) / (nitems + 1); + else + vert_spacing = (ph - (maxph + ph_adjust)) / 2; + + y = vert_spacing + ph_adjust; + x = horiz_spacing; + + /* Now flip through putting items where we want them, paying + attention to justification. */ + LIST_LOOP (rest, items) + { + /* make sure the image is instantiated */ + Lisp_Object glyph = XCAR (rest); + Lisp_Object gii = glyph_image_instance (glyph, domain, ERROR_ME, 1); + int gwidth = glyph_width (glyph, Qnil, DEFAULT_INDEX, domain); + int gheight = glyph_height (glyph, Qnil, DEFAULT_INDEX, domain); + + children = Fcons (gii, children); + + if (EQ (orient, Qhorizontal)) + { + if (EQ (justify, Qright)) + y = ph - (gheight + vert_spacing); + else if (EQ (justify, Qcenter)) + y = (ph - gheight) / 2; + } + else if (EQ (orient, Qvertical)) + { + if (EQ (justify, Qright)) + x = pw - (gwidth + horiz_spacing); + else if (EQ (justify, Qcenter)) + x = (pw - gwidth) / 2; + } + + XIMAGE_INSTANCE_XOFFSET (gii) = x; + XIMAGE_INSTANCE_YOFFSET (gii) = y; + + if (EQ (orient, Qhorizontal)) + { + x += (gwidth + horiz_spacing); + } + else if (EQ (orient, Qvertical)) + { + y += (gheight + vert_spacing); + } + } + + IMAGE_INSTANCE_LAYOUT_CHILDREN (ii) = children; + assert (pw && ph); + IMAGE_INSTANCE_SUBWINDOW_WIDTH (ii) = pw; + IMAGE_INSTANCE_SUBWINDOW_HEIGHT (ii) = ph; +} + + /************************************************************************/ /* initialization */ /************************************************************************/ @@ -498,6 +781,14 @@ defkeyword (&Q_image, ":image"); defkeyword (&Q_percent, ":percent"); defkeyword (&Q_text, ":text"); + defkeyword (&Q_orientation, ":orientation"); + defkeyword (&Q_justify, ":justify"); + defkeyword (&Q_border, ":border"); + + defsymbol (&Qetched_in, "etched-in"); + defsymbol (&Qetched_out, "etched-out"); + defsymbol (&Qbevel_in, "bevel-in"); + defsymbol (&Qbevel_out, "bevel-out"); } void @@ -536,7 +827,8 @@ IIFORMAT_HAS_SHARED_METHOD (button, possible_dest_types, widget); IIFORMAT_HAS_SHARED_METHOD (button, instantiate, widget); IIFORMAT_HAS_SHARED_METHOD (button, normalize, widget); - IIFORMAT_VALID_KEYWORD (button, Q_image, check_valid_glyph_or_image); + IIFORMAT_VALID_KEYWORD (button, + Q_image, check_valid_glyph_or_instantiator); VALID_WIDGET_KEYWORDS (button); VALID_GUI_KEYWORDS (button); @@ -552,7 +844,6 @@ INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (combo_box, "combo-box"); IIFORMAT_HAS_METHOD (combo_box, validate); IIFORMAT_HAS_SHARED_METHOD (combo_box, possible_dest_types, widget); - IIFORMAT_HAS_METHOD (combo_box, instantiate); VALID_GUI_KEYWORDS (combo_box); IIFORMAT_VALID_KEYWORD (combo_box, Q_width, check_valid_int); @@ -576,7 +867,7 @@ INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (progress_gauge, "progress-gauge"); IIFORMAT_HAS_SHARED_METHOD (progress_gauge, validate, widget); IIFORMAT_HAS_SHARED_METHOD (progress_gauge, possible_dest_types, widget); - IIFORMAT_HAS_SHARED_METHOD (progress_gauge, instantiate, combo_box); + IIFORMAT_HAS_SHARED_METHOD (progress_gauge, instantiate, widget); VALID_WIDGET_KEYWORDS (progress_gauge); VALID_GUI_KEYWORDS (progress_gauge); @@ -584,7 +875,7 @@ INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (tree_view, "tree-view"); IIFORMAT_HAS_SHARED_METHOD (tree_view, validate, combo_box); IIFORMAT_HAS_SHARED_METHOD (tree_view, possible_dest_types, widget); - IIFORMAT_HAS_SHARED_METHOD (tree_view, instantiate, combo_box); + IIFORMAT_HAS_METHOD (tree_view, instantiate); VALID_WIDGET_KEYWORDS (tree_view); VALID_GUI_KEYWORDS (tree_view); IIFORMAT_VALID_KEYWORD (tree_view, Q_properties, check_valid_item_list); @@ -605,23 +896,30 @@ VALID_WIDGET_KEYWORDS (label); IIFORMAT_VALID_KEYWORD (label, Q_descriptor, check_valid_string); -#if 0 - /* group */ - INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (group, "group"); - IIFORMAT_HAS_SHARED_METHOD (group, possible_dest_types, widget); - IIFORMAT_HAS_METHOD (group, instantiate); + /* layout */ + INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (layout, "layout"); + IIFORMAT_HAS_METHOD (layout, possible_dest_types); + IIFORMAT_HAS_METHOD (layout, instantiate); + IIFORMAT_HAS_METHOD (layout, normalize); + IIFORMAT_VALID_KEYWORD (layout, Q_pixel_width, check_valid_int); + IIFORMAT_VALID_KEYWORD (layout, Q_pixel_height, check_valid_int); + IIFORMAT_VALID_KEYWORD (layout, Q_orientation, check_valid_orientation); + IIFORMAT_VALID_KEYWORD (layout, Q_justify, check_valid_justification); + IIFORMAT_VALID_KEYWORD (layout, Q_border, check_valid_border); + IIFORMAT_VALID_KEYWORD (layout, Q_items, + check_valid_glyph_or_instantiator_list); +} - IIFORMAT_VALID_KEYWORD (group, Q_width, check_valid_int); - IIFORMAT_VALID_KEYWORD (group, Q_height, check_valid_int); - IIFORMAT_VALID_KEYWORD (group, Q_pixel_width, check_valid_int); - IIFORMAT_VALID_KEYWORD (group, Q_pixel_height, check_valid_int); - IIFORMAT_VALID_KEYWORD (group, Q_face, check_valid_face); - IIFORMAT_VALID_KEYWORD (group, Q_background, check_valid_string); - IIFORMAT_VALID_KEYWORD (group, Q_descriptor, check_valid_string); +void +reinit_vars_of_glyphs_widget (void) +{ +#ifdef DEBUG_WIDGETS + debug_widget_instances = 0; #endif } void vars_of_glyphs_widget (void) { + reinit_vars_of_glyphs_widget (); } diff -r 28d9c139be4c -r 11054d720c21 src/glyphs-x.c --- a/src/glyphs-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/glyphs-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -40,7 +40,8 @@ Many changes for color work and optimizations by Jareth Hein for 21.0 Switch of GIF/JPEG/PNG to new EImage intermediate code by Jareth Hein for 21.0 TIFF code by Jareth Hein for 21.0 - GIF/JPEG/PNG/TIFF code moved to new glyph-eimage.c for 21.0 + GIF/JPEG/PNG/TIFF code moved to new glyph-eimage.c by Andy Piper for 21.0 + Subwindow and Widget support by Andy Piper for 21.2 TODO: Convert images.el to C and stick it in here? @@ -52,7 +53,9 @@ #include "console-x.h" #include "glyphs-x.h" #include "objects-x.h" +#ifdef HAVE_WIDGETS #include "gui-x.h" +#endif #include "xmu.h" #include "buffer.h" @@ -73,7 +76,7 @@ #include "file-coding.h" #endif -#ifdef LWLIB_USES_MOTIF +#ifdef LWLIB_WIDGETS_MOTIF #include #endif #include @@ -94,6 +97,7 @@ DECLARE_IMAGE_INSTANTIATOR_FORMAT (string); DECLARE_IMAGE_INSTANTIATOR_FORMAT (formatted_string); DECLARE_IMAGE_INSTANTIATOR_FORMAT (inherit); +DECLARE_IMAGE_INSTANTIATOR_FORMAT (layout); #ifdef HAVE_JPEG DECLARE_IMAGE_INSTANTIATOR_FORMAT (jpeg); #endif @@ -122,11 +126,17 @@ DEFINE_IMAGE_INSTANTIATOR_FORMAT (autodetect); +#ifdef HAVE_WIDGETS DEFINE_DEVICE_IIFORMAT (x, widget); DEFINE_DEVICE_IIFORMAT (x, button); DEFINE_DEVICE_IIFORMAT (x, progress_gauge); DEFINE_DEVICE_IIFORMAT (x, edit_field); +#if defined (LWLIB_WIDGETS_MOTIF) && XmVERSION > 1 DEFINE_DEVICE_IIFORMAT (x, combo_box); +#endif +DEFINE_DEVICE_IIFORMAT (x, tab_control); +DEFINE_DEVICE_IIFORMAT (x, label); +#endif static void cursor_font_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, @@ -135,6 +145,11 @@ int dest_mask, Lisp_Object domain); +#ifdef HAVE_WIDGETS +static void +update_widget_face (struct Lisp_Image_Instance* ii, Lisp_Object domain); +#endif + #include "bitmaps.h" @@ -357,6 +372,10 @@ } } +#ifdef DEBUG_WIDGETS +extern int debug_widget_instances; +#endif + static void x_finalize_image_instance (struct Lisp_Image_Instance *p) { @@ -371,8 +390,12 @@ { if (IMAGE_INSTANCE_SUBWINDOW_ID (p)) { - XtUnmanageChild (IMAGE_INSTANCE_X_WIDGET_ID (p)); - XtDestroyWidget (IMAGE_INSTANCE_X_WIDGET_ID (p)); +#ifdef DEBUG_WIDGETS + debug_widget_instances--; + stderr_out ("widget destroyed, %d left\n", debug_widget_instances); +#endif + lw_destroy_widget (IMAGE_INSTANCE_X_WIDGET_ID (p)); + lw_destroy_widget (IMAGE_INSTANCE_X_CLIPWIDGET (p)); IMAGE_INSTANCE_SUBWINDOW_ID (p) = 0; } } @@ -384,14 +407,27 @@ } else { - if (IMAGE_INSTANCE_X_PIXMAP (p)) - XFreePixmap (dpy, IMAGE_INSTANCE_X_PIXMAP (p)); + int i; + if (IMAGE_INSTANCE_PIXMAP_TIMEOUT (p)) + disable_glyph_animated_timeout (IMAGE_INSTANCE_PIXMAP_TIMEOUT (p)); + if (IMAGE_INSTANCE_X_MASK (p) && IMAGE_INSTANCE_X_MASK (p) != IMAGE_INSTANCE_X_PIXMAP (p)) XFreePixmap (dpy, IMAGE_INSTANCE_X_MASK (p)); - IMAGE_INSTANCE_X_PIXMAP (p) = 0; - IMAGE_INSTANCE_X_MASK (p) = 0; + IMAGE_INSTANCE_PIXMAP_MASK (p) = 0; + if (IMAGE_INSTANCE_X_PIXMAP_SLICES (p)) + { + for (i = 0; i < IMAGE_INSTANCE_PIXMAP_MAXSLICE (p); i++) + if (IMAGE_INSTANCE_X_PIXMAP_SLICE (p,i)) + { + XFreePixmap (dpy, IMAGE_INSTANCE_X_PIXMAP_SLICE (p,i)); + IMAGE_INSTANCE_X_PIXMAP_SLICE (p, i) = 0; + } + xfree (IMAGE_INSTANCE_X_PIXMAP_SLICES (p)); + IMAGE_INSTANCE_X_PIXMAP_SLICES (p) = 0; + } + if (IMAGE_INSTANCE_X_CURSOR (p)) { XFreeCursor (dpy, IMAGE_INSTANCE_X_CURSOR (p)); @@ -408,7 +444,13 @@ } } } - if (IMAGE_INSTANCE_X_PIXELS (p)) + /* You can sometimes have pixels without a live device. I forget + why, but that's why we free them here if we have a pixmap type + image instance. It probably means that we might also get a memory + leak with widgets. */ + if (IMAGE_INSTANCE_TYPE (p) != IMAGE_WIDGET + && IMAGE_INSTANCE_TYPE (p) != IMAGE_SUBWINDOW + && IMAGE_INSTANCE_X_PIXELS (p)) { xfree (IMAGE_INSTANCE_X_PIXELS (p)); IMAGE_INSTANCE_X_PIXELS (p) = 0; @@ -460,9 +502,13 @@ static void x_initialize_pixmap_image_instance (struct Lisp_Image_Instance *ii, + int slices, enum image_instance_type type) { ii->data = xnew_and_zero (struct x_image_instance_data); + IMAGE_INSTANCE_PIXMAP_MAXSLICE (ii) = slices; + IMAGE_INSTANCE_X_PIXMAP_SLICES (ii) = + xnew_array_and_zero (Pixmap, slices); IMAGE_INSTANCE_TYPE (ii) = type; IMAGE_INSTANCE_PIXMAP_FILENAME (ii) = Qnil; IMAGE_INSTANCE_PIXMAP_MASK_FILENAME (ii) = Qnil; @@ -781,6 +827,7 @@ Colormap cmap, unsigned long *pixels, int npixels, + int slices, Lisp_Object instantiator) { Lisp_Object device = IMAGE_INSTANCE_DEVICE (ii); @@ -816,13 +863,15 @@ XFreeGC (dpy, gc); - x_initialize_pixmap_image_instance (ii, IMAGE_COLOR_PIXMAP); + x_initialize_pixmap_image_instance (ii, slices, IMAGE_COLOR_PIXMAP); IMAGE_INSTANCE_PIXMAP_FILENAME (ii) = find_keyword_in_vector (instantiator, Q_file); + /* Fixup a set of pixmaps. */ IMAGE_INSTANCE_X_PIXMAP (ii) = pixmap; - IMAGE_INSTANCE_X_MASK (ii) = 0; + + IMAGE_INSTANCE_PIXMAP_MASK (ii) = 0; IMAGE_INSTANCE_PIXMAP_WIDTH (ii) = ximage->width; IMAGE_INSTANCE_PIXMAP_HEIGHT (ii) = ximage->height; IMAGE_INSTANCE_PIXMAP_DEPTH (ii) = ximage->depth; @@ -832,8 +881,44 @@ } static void +image_instance_add_x_image (struct Lisp_Image_Instance *ii, + XImage *ximage, + int slice, + Lisp_Object instantiator) +{ + Lisp_Object device = IMAGE_INSTANCE_DEVICE (ii); + Display *dpy; + GC gc; + Drawable d; + Pixmap pixmap; + + dpy = DEVICE_X_DISPLAY (XDEVICE (device)); + d = XtWindow(DEVICE_XT_APP_SHELL (XDEVICE (device))); + + pixmap = XCreatePixmap (dpy, d, ximage->width, + ximage->height, ximage->depth); + if (!pixmap) + signal_simple_error ("Unable to create pixmap", instantiator); + + gc = XCreateGC (dpy, pixmap, 0, NULL); + if (!gc) + { + XFreePixmap (dpy, pixmap); + signal_simple_error ("Unable to create GC", instantiator); + } + + XPutImage (dpy, pixmap, gc, ximage, 0, 0, 0, 0, + ximage->width, ximage->height); + + XFreeGC (dpy, gc); + + IMAGE_INSTANCE_X_PIXMAP_SLICE (ii, slice) = pixmap; +} + +static void x_init_image_instance_from_eimage (struct Lisp_Image_Instance *ii, int width, int height, + int slices, unsigned char *eimage, int dest_mask, Lisp_Object instantiator, @@ -843,29 +928,38 @@ Colormap cmap = DEVICE_X_COLORMAP (XDEVICE(device)); unsigned long *pixtbl = NULL; int npixels = 0; + int slice; XImage* ximage; - ximage = convert_EImage_to_XImage (device, width, height, eimage, - &pixtbl, &npixels); - if (!ximage) + for (slice = 0; slice < slices; slice++) { - if (pixtbl) xfree (pixtbl); - signal_image_error("EImage to XImage conversion failed", instantiator); - } - - /* Now create the pixmap and set up the image instance */ - init_image_instance_from_x_image (ii, ximage, dest_mask, - cmap, pixtbl, npixels, - instantiator); - - if (ximage) - { - if (ximage->data) - { - xfree (ximage->data); - ximage->data = 0; - } - XDestroyImage (ximage); + ximage = convert_EImage_to_XImage (device, width, height, + eimage + (width * height * 3 * slice), + &pixtbl, &npixels); + if (!ximage) + { + if (pixtbl) xfree (pixtbl); + signal_image_error("EImage to XImage conversion failed", instantiator); + } + + /* Now create the pixmap and set up the image instance */ + if (slice == 0) + init_image_instance_from_x_image (ii, ximage, dest_mask, + cmap, pixtbl, npixels, slices, + instantiator); + else + image_instance_add_x_image (ii, ximage, slice, instantiator); + + if (ximage) + { + if (ximage->data) + { + xfree (ximage->data); + ximage->data = 0; + } + XDestroyImage (ximage); + ximage = 0; + } } } @@ -940,7 +1034,7 @@ IMAGE_MONO_PIXMAP_MASK | IMAGE_COLOR_PIXMAP_MASK | IMAGE_POINTER_MASK); - x_initialize_pixmap_image_instance (ii, type); + x_initialize_pixmap_image_instance (ii, 1, type); IMAGE_INSTANCE_PIXMAP_WIDTH (ii) = width; IMAGE_INSTANCE_PIXMAP_HEIGHT (ii) = height; IMAGE_INSTANCE_PIXMAP_FILENAME (ii) = @@ -1244,7 +1338,7 @@ visual = DEVICE_X_VISUAL (XDEVICE(device)); #endif - x_initialize_pixmap_image_instance (ii, type); + x_initialize_pixmap_image_instance (ii, 1, type); assert (!NILP (data)); @@ -1354,7 +1448,7 @@ pixels = NULL; IMAGE_INSTANCE_X_PIXMAP (ii) = pixmap; - IMAGE_INSTANCE_X_MASK (ii) = mask; + IMAGE_INSTANCE_PIXMAP_MASK (ii) = (void*)mask; IMAGE_INSTANCE_X_COLORMAP (ii) = cmap; IMAGE_INSTANCE_X_PIXELS (ii) = pixels; IMAGE_INSTANCE_X_NPIXELS (ii) = npixels; @@ -1882,7 +1976,7 @@ /* #### call XQueryTextExtents() and check_pointer_sizes() here. */ - x_initialize_pixmap_image_instance (ii, IMAGE_POINTER); + x_initialize_pixmap_image_instance (ii, 1, IMAGE_POINTER); IMAGE_INSTANCE_X_CURSOR (ii) = XCreateGlyphCursor (dpy, source, mask, source_char, mask_char, &fg, &bg); @@ -1935,7 +2029,7 @@ if ((i = XmuCursorNameToIndex (name_ext)) == -1) signal_simple_error ("Unrecognized cursor-font name", data); - x_initialize_pixmap_image_instance (ii, IMAGE_POINTER); + x_initialize_pixmap_image_instance (ii, 1, IMAGE_POINTER); IMAGE_INSTANCE_X_CURSOR (ii) = XCreateFontCursor (dpy, i); foreground = find_keyword_in_vector (instantiator, Q_foreground); if (NILP (foreground)) @@ -1960,7 +2054,7 @@ IMAGE_INSTANCE_TYPE (p) = IMAGE_COLOR_PIXMAP; /* Make sure there aren't two pointers to the same mask, causing it to get freed twice. */ - IMAGE_INSTANCE_X_MASK (p) = 0; + IMAGE_INSTANCE_PIXMAP_MASK (p) = 0; break; default: @@ -2008,33 +2102,41 @@ if (IMAGE_INSTANCE_TYPE (p) == IMAGE_SUBWINDOW) { XUnmapWindow - (DisplayOfScreen (IMAGE_INSTANCE_X_SUBWINDOW_SCREEN (p)), - IMAGE_INSTANCE_X_SUBWINDOW_ID (p)); + (IMAGE_INSTANCE_X_SUBWINDOW_DISPLAY (p), + IMAGE_INSTANCE_X_CLIPWINDOW (p)); } else /* must be a widget */ { - XtUnmapWidget (IMAGE_INSTANCE_X_WIDGET_ID (p)); + XtUnmapWidget (IMAGE_INSTANCE_X_CLIPWIDGET (p)); } } /* map the subwindow. This is used by redisplay via redisplay_output_subwindow */ static void -x_map_subwindow (struct Lisp_Image_Instance *p, int x, int y) +x_map_subwindow (struct Lisp_Image_Instance *p, int x, int y, + struct display_glyph_area* dga) { if (IMAGE_INSTANCE_TYPE (p) == IMAGE_SUBWINDOW) { Window subwindow = IMAGE_INSTANCE_X_SUBWINDOW_ID (p); - Screen* screen = IMAGE_INSTANCE_X_SUBWINDOW_SCREEN (p); - XMapWindow (DisplayOfScreen (screen), subwindow); - XMoveWindow (DisplayOfScreen (screen), subwindow, x, y); + XMoveResizeWindow (IMAGE_INSTANCE_X_SUBWINDOW_DISPLAY (p), + IMAGE_INSTANCE_X_CLIPWINDOW (p), + x, y, dga->width, dga->height); + XMoveWindow (IMAGE_INSTANCE_X_SUBWINDOW_DISPLAY (p), + subwindow, -dga->xoffset, -dga->yoffset); + XMapWindow (IMAGE_INSTANCE_X_SUBWINDOW_DISPLAY (p), + IMAGE_INSTANCE_X_CLIPWINDOW (p)); } else /* must be a widget */ { - XtMoveWidget (IMAGE_INSTANCE_X_WIDGET_ID (p), - x + IMAGE_INSTANCE_X_WIDGET_XOFFSET (p), - y + IMAGE_INSTANCE_X_WIDGET_YOFFSET (p)); - XtMapWidget (IMAGE_INSTANCE_X_WIDGET_ID (p)); + XtConfigureWidget (IMAGE_INSTANCE_X_CLIPWIDGET (p), + x + IMAGE_INSTANCE_X_WIDGET_XOFFSET (p), + y + IMAGE_INSTANCE_X_WIDGET_YOFFSET (p), + dga->width, dga->height, 0); + XtMoveWidget (IMAGE_INSTANCE_X_WIDGET_ID (p), + -dga->xoffset, -dga->yoffset); + XtMapWidget (IMAGE_INSTANCE_X_CLIPWIDGET (p)); } } @@ -2043,14 +2145,47 @@ static void x_update_subwindow (struct Lisp_Image_Instance *p) { +#ifdef HAVE_WIDGETS if (IMAGE_INSTANCE_TYPE (p) == IMAGE_WIDGET) { - widget_value* wv = xmalloc_widget_value (); - button_item_to_widget_value (IMAGE_INSTANCE_WIDGET_SINGLE_ITEM (p), - wv, 1, 1); + Arg al[5]; + widget_value* wv = gui_items_to_widget_values + (IMAGE_INSTANCE_WIDGET_ITEMS (p)); + + /* This seems ugly, but I'm not sure what else to do. */ + if (EQ (IMAGE_INSTANCE_WIDGET_TYPE (p), Qtab_control)) + { + widget_value* cur = 0; + /* Give each child label the correct foreground color. */ + Lisp_Object pixel = FACE_FOREGROUND + (IMAGE_INSTANCE_WIDGET_FACE (p), + IMAGE_INSTANCE_SUBWINDOW_FRAME (p)); + XColor fcolor = COLOR_INSTANCE_X_COLOR (XCOLOR_INSTANCE (pixel)); + XtSetArg (al [0], XtNtabForeground, fcolor.pixel); + + for (cur = wv->contents; cur; cur = cur->next) + { + if (cur->value) + { + cur->nargs = 1; + cur->args = al; + } + } + } + + /* now modify the widget */ lw_modify_all_widgets (IMAGE_INSTANCE_X_WIDGET_LWID (p), - wv, 1); + wv, True); + free_widget_value_tree (wv); + /* update the colors and font */ + update_widget_face (p, IMAGE_INSTANCE_SUBWINDOW_FRAME (p)); + /* We have to do this otherwise Motif will unceremoniously + resize us when the label gets set. */ + XtSetArg (al [0], XtNwidth, IMAGE_INSTANCE_WIDGET_WIDTH (p)); + XtSetArg (al [1], XtNheight, IMAGE_INSTANCE_WIDGET_HEIGHT (p)); + XtSetValues (IMAGE_INSTANCE_X_WIDGET_ID (p), al, 2); } +#endif } /* instantiate and x type subwindow */ @@ -2085,14 +2220,22 @@ ii->data = xnew_and_zero (struct x_subwindow_data); IMAGE_INSTANCE_X_SUBWINDOW_PARENT (ii) = pw; - IMAGE_INSTANCE_X_SUBWINDOW_SCREEN (ii) = xs; + IMAGE_INSTANCE_X_SUBWINDOW_DISPLAY (ii) = DisplayOfScreen (xs); xswa.backing_store = Always; valueMask |= CWBackingStore; xswa.colormap = DefaultColormapOfScreen (xs); valueMask |= CWColormap; - win = XCreateWindow (dpy, pw, 0, 0, w, h, 0, CopyFromParent, + /* Create a window for clipping */ + IMAGE_INSTANCE_X_CLIPWINDOW (ii) = + XCreateWindow (dpy, pw, 0, 0, w, h, 0, CopyFromParent, + InputOutput, CopyFromParent, valueMask, + &xswa); + + /* Now put the subwindow inside the clip window. */ + win = XCreateWindow (dpy, IMAGE_INSTANCE_X_CLIPWINDOW (ii), + 0, 0, w, h, 0, CopyFromParent, InputOutput, CopyFromParent, valueMask, &xswa); @@ -2134,24 +2277,77 @@ { if (IMAGE_INSTANCE_TYPE (ii) == IMAGE_SUBWINDOW) { - XResizeWindow (DisplayOfScreen (IMAGE_INSTANCE_X_SUBWINDOW_SCREEN (ii)), + XResizeWindow (IMAGE_INSTANCE_X_SUBWINDOW_DISPLAY (ii), IMAGE_INSTANCE_X_SUBWINDOW_ID (ii), w, h); } else /* must be a widget */ { Arg al[2]; + + if (!XtIsRealized (IMAGE_INSTANCE_X_WIDGET_ID (ii))) + { + Lisp_Object sw; + XSETIMAGE_INSTANCE (sw, ii); + signal_simple_error ("XEmacs bug: subwindow is not realized", sw); + } + XtSetArg (al [0], XtNwidth, (Dimension)w); XtSetArg (al [1], XtNheight, (Dimension)h); XtSetValues (IMAGE_INSTANCE_X_WIDGET_ID (ii), al, 2); } } + +#ifdef HAVE_WIDGETS + /************************************************************************/ /* widgets */ /************************************************************************/ static void +update_widget_face (struct Lisp_Image_Instance* ii, Lisp_Object domain) +{ + Arg al[3]; +#ifdef LWLIB_WIDGETS_MOTIF + XmFontList fontList; +#endif + + Lisp_Object pixel = FACE_FOREGROUND + (IMAGE_INSTANCE_WIDGET_FACE (ii), + IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); + XColor fcolor = COLOR_INSTANCE_X_COLOR (XCOLOR_INSTANCE (pixel)); + XColor bcolor; + + pixel = FACE_BACKGROUND + (IMAGE_INSTANCE_WIDGET_FACE (ii), + IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); + bcolor = COLOR_INSTANCE_X_COLOR (XCOLOR_INSTANCE (pixel)); + + XtSetArg (al [0], XtNbackground, bcolor.pixel); + XtSetArg (al [1], XtNforeground, fcolor.pixel); + +#ifdef LWLIB_WIDGETS_MOTIF + fontList = XmFontListCreate + (FONT_INSTANCE_X_FONT + (XFONT_INSTANCE (widget_face_font_info + (domain, IMAGE_INSTANCE_WIDGET_FACE (ii), + 0, 0))), XmSTRING_DEFAULT_CHARSET); + XtSetArg (al [2], XmNfontList, fontList ); +#else + XtSetArg (al [2], XtNfont, (void*)FONT_INSTANCE_X_FONT + (XFONT_INSTANCE (widget_face_font_info + (domain, + IMAGE_INSTANCE_WIDGET_FACE (ii), + 0, 0)))); +#endif + XtSetValues (IMAGE_INSTANCE_X_WIDGET_ID (ii), al, 3); +#ifdef LWLIB_WIDGETS_MOTIF + XmFontListFree (fontList); +#endif +} + +static void x_widget_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, Lisp_Object pointer_fg, Lisp_Object pointer_bg, int dest_mask, Lisp_Object domain, @@ -2162,18 +2358,16 @@ struct device* d = XDEVICE (device); Lisp_Object frame = FW_FRAME (domain); struct frame* f = XFRAME (frame); - XColor fcolor, bcolor; - Extbyte* nm=0; + char* nm=0; Widget wid; Arg al [32]; int ac = 0; int id = new_lwlib_id (); -#ifdef LWLIB_USES_MOTIF - XmFontList fontList; -#endif + widget_value* clip_wv; + XColor fcolor, bcolor; if (!DEVICE_X_P (d)) - signal_simple_error ("Not an mswindows device", device); + signal_simple_error ("Not an X device", device); /* have to set the type this late in case there is no device instantiation for a widget. But we can go ahead and do it without @@ -2185,15 +2379,46 @@ ii->data = xnew_and_zero (struct x_subwindow_data); + /* Create a clip window to contain the subwidget. Incredibly the + XEmacs manager seems to be the most appropriate widget for + this. Nothing else is simple enough and yet does what is + required. */ + clip_wv = xmalloc_widget_value (); + + XtSetArg (al [ac], XtNresize, False); ac++; + XtSetArg (al [ac], XtNwidth, + (Dimension)IMAGE_INSTANCE_SUBWINDOW_WIDTH (ii)); ac++; + XtSetArg (al [ac], XtNheight, + (Dimension)IMAGE_INSTANCE_SUBWINDOW_HEIGHT (ii)); ac++; + + clip_wv->enabled = True; + clip_wv->nargs = ac; + clip_wv->args = al; + clip_wv->name = xstrdup ("clip-window"); + clip_wv->value = xstrdup ("clip-window"); + + IMAGE_INSTANCE_X_CLIPWIDGET (ii) + = lw_create_widget ("clip-window", "clip-window", new_lwlib_id (), + clip_wv, FRAME_X_CONTAINER_WIDGET (f), + False, 0, 0, 0); + + free_widget_value_tree (clip_wv); + /* copy any args we were given */ + ac = 0; + if (wv->nargs) lw_add_value_args_to_args (wv, al, &ac); - /* add our own arguments */ + /* Fixup the colors. We have to do this *before* the widget gets + created so that Motif will fix up the shadow colors + correctly. Once the widget is created Motif won't do this + anymore...*/ pixel = FACE_FOREGROUND (IMAGE_INSTANCE_WIDGET_FACE (ii), IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); fcolor = COLOR_INSTANCE_X_COLOR (XCOLOR_INSTANCE (pixel)); + pixel = FACE_BACKGROUND (IMAGE_INSTANCE_WIDGET_FACE (ii), IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); @@ -2201,49 +2426,44 @@ XtSetArg (al [ac], XtNbackground, bcolor.pixel); ac++; XtSetArg (al [ac], XtNforeground, fcolor.pixel); ac++; -#ifdef LWLIB_USES_MOTIF - fontList = XmFontListCreate - ((void*)FONT_INSTANCE_X_FONT - (XFONT_INSTANCE (widget_face_font_info - (domain, IMAGE_INSTANCE_WIDGET_FACE (ii), - 0, 0))), XmSTRING_DEFAULT_CHARSET); - XtSetArg (al [ac], XmNfontList, fontList ); ac++; -#else - XtSetArg (al [ac], XtNfont, (void*)FONT_INSTANCE_X_FONT - (XFONT_INSTANCE (widget_face_font_info - (domain, - IMAGE_INSTANCE_WIDGET_FACE (ii), - 0, 0)))); ac++; -#endif + /* we cannot allow widgets to resize themselves */ + XtSetArg (al [ac], XtNresize, False); ac++; + XtSetArg (al [ac], XtNwidth, + (Dimension)IMAGE_INSTANCE_SUBWINDOW_WIDTH (ii)); ac++; + XtSetArg (al [ac], XtNheight, + (Dimension)IMAGE_INSTANCE_SUBWINDOW_HEIGHT (ii)); ac++; wv->nargs = ac; wv->args = al; - - wid = lw_create_widget (type, wv->name, id, wv, FRAME_X_CONTAINER_WIDGET (f), + + wid = lw_create_widget (type, wv->name, id, wv, IMAGE_INSTANCE_X_CLIPWIDGET (ii), False, 0, popup_selection_callback, 0); + IMAGE_INSTANCE_SUBWINDOW_ID (ii) = (void*)wid; IMAGE_INSTANCE_X_WIDGET_LWID (ii) = id; -#ifdef LWLIB_USES_MOTIF - XmFontListFree (fontList); -#endif - /* because the EmacsManager is the widgets parent we have to - offset the redisplay of the widget by the amount the text - widget is inside the manager. */ + + /* update the font. */ + update_widget_face (ii, domain); + + /* Resize the widget here so that the values do not get copied by + lwlib. */ ac = 0; XtSetArg (al [ac], XtNwidth, (Dimension)IMAGE_INSTANCE_SUBWINDOW_WIDTH (ii)); ac++; XtSetArg (al [ac], XtNheight, (Dimension)IMAGE_INSTANCE_SUBWINDOW_HEIGHT (ii)); ac++; - XtSetValues (wid, al, ac); - /* finally get offsets in the frame */ + XtSetValues (IMAGE_INSTANCE_X_WIDGET_ID (ii), al, ac); + /* because the EmacsManager is the widgets parent we have to + offset the redisplay of the widget by the amount the text + widget is inside the manager. */ ac = 0; XtSetArg (al [ac], XtNx, &IMAGE_INSTANCE_X_WIDGET_XOFFSET (ii)); ac++; XtSetArg (al [ac], XtNy, &IMAGE_INSTANCE_X_WIDGET_YOFFSET (ii)); ac++; XtGetValues (FRAME_X_TEXT_WIDGET (f), al, ac); - IMAGE_INSTANCE_SUBWINDOW_ID (ii) = (void*)wid; - - free_widget_value (wv); + XtMapWidget (wid); + + free_widget_value_tree (wv); } static Lisp_Object @@ -2254,7 +2474,7 @@ if (EQ (prop, Q_text)) { - Extbyte* str=0; + char* str; widget_value* wv = lw_get_all_values (IMAGE_INSTANCE_X_WIDGET_LWID (ii)); CHECK_STRING (val); GET_C_STRING_OS_DATA_ALLOCA (val, str); @@ -2262,6 +2482,12 @@ lw_modify_all_widgets (IMAGE_INSTANCE_X_WIDGET_LWID (ii), wv, False); return Qt; } + /* Modify the face properties of the widget */ + if (EQ (prop, Q_face)) + { + update_widget_face (ii, IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); + return Qt; + } return Qunbound; } @@ -2311,7 +2537,7 @@ { Arg al [2]; int ac =0; -#ifdef LWLIB_USES_MOTIF +#ifdef LWLIB_WIDGETS_MOTIF XtSetArg (al [ac], XmNlabelType, XmPIXMAP); ac++; XtSetArg (al [ac], XmNlabelPixmap, XIMAGE_INSTANCE_X_PIXMAP (glyph));ac++; #else @@ -2389,6 +2615,7 @@ pointer_bg, dest_mask, domain, "text-field", wv); } +#if defined (LWLIB_WIDGETS_MOTIF) && XmVERSION > 1 /* instantiate a combo control */ static void x_combo_box_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, @@ -2396,28 +2623,117 @@ int dest_mask, Lisp_Object domain) { struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); - Lisp_Object rest; - Lisp_Object gui = IMAGE_INSTANCE_WIDGET_ITEM (ii); - widget_value* wv = xmalloc_widget_value (); - - button_item_to_widget_value (gui, wv, 1, 1); + widget_value * wv = 0; + /* This is not done generically because of sizing problems under + mswindows. */ + widget_instantiate_1 (image_instance, instantiator, pointer_fg, + pointer_bg, dest_mask, domain, 1, 0, 0); + + wv = gui_items_to_widget_values (IMAGE_INSTANCE_WIDGET_ITEMS (ii)); x_widget_instantiate (image_instance, instantiator, pointer_fg, pointer_bg, dest_mask, domain, "combo-box", wv); - /* add items to the combo box */ - LIST_LOOP (rest, Fplist_get (IMAGE_INSTANCE_WIDGET_PROPS (ii), Q_items, Qnil)) +} +#endif + +static void +x_tab_control_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, + Lisp_Object pointer_fg, Lisp_Object pointer_bg, + int dest_mask, Lisp_Object domain) +{ + struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); + Arg al [1]; + XColor fcolor; + Lisp_Object pixel; + widget_value* cur; + + widget_value * wv = + gui_items_to_widget_values (IMAGE_INSTANCE_WIDGET_ITEMS (ii)); + + /* Give each child label the correct foreground color. */ + pixel = FACE_FOREGROUND + (IMAGE_INSTANCE_WIDGET_FACE (ii), + IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); + fcolor = COLOR_INSTANCE_X_COLOR (XCOLOR_INSTANCE (pixel)); + XtSetArg (al [0], XtNtabForeground, fcolor.pixel); + + for (cur = wv->contents; cur; cur = cur->next) + { + if (cur->value) + { + cur->nargs = 1; + cur->args = al; + } + } + + x_widget_instantiate (image_instance, instantiator, pointer_fg, + pointer_bg, dest_mask, domain, "tab-control", wv); +} + +/* set the properties of a tab control */ +static Lisp_Object +x_tab_control_set_property (Lisp_Object image_instance, Lisp_Object prop, + Lisp_Object val) +{ + struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); + + if (EQ (prop, Q_items)) { -#if 0 - Extbyte* str; - XmString xmstr; - GET_C_STRING_OS_DATA_ALLOCA (XCAR (rest), str); - xmstr = XmStringCreate (str, XmSTRING_DEFAULT_CHARSET); - XmListAddItem (IMAGE_INSTANCE_X_WIDGET_ID (ii), xmstr, 0); - XmStringFree (xmstr); -#endif + widget_value * wv = 0, *cur; + Arg al [1]; + XColor fcolor; + Lisp_Object pixel; + + check_valid_item_list_1 (val); + + IMAGE_INSTANCE_WIDGET_ITEMS (ii) = + Fcons (XCAR (IMAGE_INSTANCE_WIDGET_ITEMS (ii)), + parse_gui_item_tree_children (val)); + + wv = gui_items_to_widget_values (IMAGE_INSTANCE_WIDGET_ITEMS (ii)); + + /* Give each child label the correct foreground color. */ + pixel = FACE_FOREGROUND + (IMAGE_INSTANCE_WIDGET_FACE (ii), + IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); + fcolor = COLOR_INSTANCE_X_COLOR (XCOLOR_INSTANCE (pixel)); + XtSetArg (al [0], XtNtabForeground, fcolor.pixel); + + for (cur = wv->contents; cur; cur = cur->next) + { + if (cur->value) + { + cur->nargs = 1; + cur->args = al; + } + } + + lw_modify_all_widgets (IMAGE_INSTANCE_X_WIDGET_LWID (ii), wv, True); + + free_widget_value_tree (wv); + return Qt; } + + return Qunbound; } +/* instantiate a static control possible for putting other things in */ +static void +x_label_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, + Lisp_Object pointer_fg, Lisp_Object pointer_bg, + int dest_mask, Lisp_Object domain) +{ + struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); + Lisp_Object gui = IMAGE_INSTANCE_WIDGET_ITEM (ii); + widget_value* wv = xmalloc_widget_value (); + + button_item_to_widget_value (gui, wv, 1, 1); + + x_widget_instantiate (image_instance, instantiator, pointer_fg, + pointer_bg, dest_mask, domain, "button", wv); +} +#endif /* HAVE_WIDGETS */ + /************************************************************************/ /* initialization */ @@ -2454,6 +2770,7 @@ { IIFORMAT_VALID_CONSOLE (x, nothing); IIFORMAT_VALID_CONSOLE (x, string); + IIFORMAT_VALID_CONSOLE (x, layout); IIFORMAT_VALID_CONSOLE (x, formatted_string); IIFORMAT_VALID_CONSOLE (x, inherit); #ifdef HAVE_XPM @@ -2477,7 +2794,7 @@ INITIALIZE_DEVICE_IIFORMAT (x, subwindow); IIFORMAT_HAS_DEVMETHOD (x, subwindow, instantiate); -#ifdef LWLIB_USES_MOTIF +#ifdef HAVE_WIDGETS /* button widget */ INITIALIZE_DEVICE_IIFORMAT (x, button); IIFORMAT_HAS_DEVMETHOD (x, button, property); @@ -2493,11 +2810,19 @@ /* text field */ INITIALIZE_DEVICE_IIFORMAT (x, edit_field); IIFORMAT_HAS_DEVMETHOD (x, edit_field, instantiate); -#if 0 /* XmVERSION > 1*/ +#if defined (LWLIB_WIDGETS_MOTIF) && XmVERSION > 1 /* combo box */ INITIALIZE_DEVICE_IIFORMAT (x, combo_box); IIFORMAT_HAS_DEVMETHOD (x, combo_box, instantiate); + IIFORMAT_HAS_SHARED_DEVMETHOD (x, combo_box, set_property, tab_control); #endif + /* tab control widget */ + INITIALIZE_DEVICE_IIFORMAT (x, tab_control); + IIFORMAT_HAS_DEVMETHOD (x, tab_control, instantiate); + IIFORMAT_HAS_DEVMETHOD (x, tab_control, set_property); + /* label */ + INITIALIZE_DEVICE_IIFORMAT (x, label); + IIFORMAT_HAS_DEVMETHOD (x, label, instantiate); #endif INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (cursor_font, "cursor-font"); IIFORMAT_VALID_CONSOLE (x, cursor_font); diff -r 28d9c139be4c -r 11054d720c21 src/glyphs-x.h --- a/src/glyphs-x.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/glyphs-x.h Mon Aug 13 11:26:11 2007 +0200 @@ -39,8 +39,7 @@ struct x_image_instance_data { - Pixmap pixmap; - Pixmap mask; + Pixmap* pixmaps; Cursor cursor; /* If depth>0, then that means that other colors were allocated when @@ -56,8 +55,13 @@ #define X_IMAGE_INSTANCE_DATA(i) ((struct x_image_instance_data *) (i)->data) -#define IMAGE_INSTANCE_X_PIXMAP(i) (X_IMAGE_INSTANCE_DATA (i)->pixmap) -#define IMAGE_INSTANCE_X_MASK(i) (X_IMAGE_INSTANCE_DATA (i)->mask) +#define IMAGE_INSTANCE_X_PIXMAP(i) (X_IMAGE_INSTANCE_DATA (i)->pixmaps[0]) +#define IMAGE_INSTANCE_X_PIXMAP_SLICE(i,slice) \ + (X_IMAGE_INSTANCE_DATA (i)->pixmaps[slice]) +#define IMAGE_INSTANCE_X_PIXMAP_SLICES(i) \ + (X_IMAGE_INSTANCE_DATA (i)->pixmaps) +#define IMAGE_INSTANCE_X_MASK(i) \ + (Pixmap)(IMAGE_INSTANCE_PIXMAP_MASK (i)) #define IMAGE_INSTANCE_X_CURSOR(i) (X_IMAGE_INSTANCE_DATA (i)->cursor) #define IMAGE_INSTANCE_X_COLORMAP(i) (X_IMAGE_INSTANCE_DATA (i)->colormap) #define IMAGE_INSTANCE_X_PIXELS(i) (X_IMAGE_INSTANCE_DATA (i)->pixels) @@ -65,6 +69,10 @@ #define XIMAGE_INSTANCE_X_PIXMAP(i) \ IMAGE_INSTANCE_X_PIXMAP (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_X_PIXMAP_SLICES(i) \ + IMAGE_INSTANCE_X_PIXMAP_SLICES (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_X_PIXMAP_SLICE(i) \ + IMAGE_INSTANCE_X_PIXMAP_SLICE (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_X_MASK(i) \ IMAGE_INSTANCE_X_MASK (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_X_CURSOR(i) \ @@ -84,11 +92,13 @@ { struct { - Screen *xscreen; + Display *display; Window parent_window; + Window clip_window; } sub; struct { + Widget clip_window; Position x_offset; Position y_offset; LWLIB_ID id; @@ -98,26 +108,34 @@ #define X_SUBWINDOW_INSTANCE_DATA(i) ((struct x_subwindow_data *) (i)->data) -#define IMAGE_INSTANCE_X_SUBWINDOW_SCREEN(i) \ - (X_SUBWINDOW_INSTANCE_DATA (i)->data.sub.xscreen) +#define IMAGE_INSTANCE_X_SUBWINDOW_DISPLAY(i) \ + (X_SUBWINDOW_INSTANCE_DATA (i)->data.sub.display) #define IMAGE_INSTANCE_X_SUBWINDOW_PARENT(i) \ (X_SUBWINDOW_INSTANCE_DATA (i)->data.sub.parent_window) +#define IMAGE_INSTANCE_X_CLIPWINDOW(i) \ + (X_SUBWINDOW_INSTANCE_DATA (i)->data.sub.clip_window) #define IMAGE_INSTANCE_X_WIDGET_XOFFSET(i) \ (X_SUBWINDOW_INSTANCE_DATA (i)->data.wid.x_offset) #define IMAGE_INSTANCE_X_WIDGET_YOFFSET(i) \ (X_SUBWINDOW_INSTANCE_DATA (i)->data.wid.y_offset) #define IMAGE_INSTANCE_X_WIDGET_LWID(i) \ (X_SUBWINDOW_INSTANCE_DATA (i)->data.wid.id) +#define IMAGE_INSTANCE_X_CLIPWIDGET(i) \ + (X_SUBWINDOW_INSTANCE_DATA (i)->data.wid.clip_window) #define XIMAGE_INSTANCE_X_SUBWINDOW_PARENT(i) \ IMAGE_INSTANCE_X_SUBWINDOW_PARENT (XIMAGE_INSTANCE (i)) -#define XIMAGE_INSTANCE_X_SUBWINDOW_SCREEN(i) \ - IMAGE_INSTANCE_X_SUBWINDOW_SCREEN (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_X_SUBWINDOW_DISPLAY(i) \ + IMAGE_INSTANCE_X_SUBWINDOW_DISPLAY (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_X_WIDGET_XOFFSET(i) \ IMAGE_INSTANCE_X_WIDGET_XOFFSET (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_X_WIDGET_YOFFSET(i) \ IMAGE_INSTANCE_X_WIDGET_YOFFSET (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_X_WIDGET_LWID(i) \ IMAGE_INSTANCE_X_WIDGET_LWID (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_X_CLIPWIDGET(i) \ + IMAGE_INSTANCE_X_CLIPWIDGET (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_X_CLIPWINDOW(i) \ + IMAGE_INSTANCE_X_CLIPWINDOW (XIMAGE_INSTANCE (i)) #define IMAGE_INSTANCE_X_SUBWINDOW_ID(i) \ ((Window) IMAGE_INSTANCE_SUBWINDOW_ID (i)) #define IMAGE_INSTANCE_X_WIDGET_ID(i) \ diff -r 28d9c139be4c -r 11054d720c21 src/glyphs.c --- a/src/glyphs.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/glyphs.c Mon Aug 13 11:26:11 2007 +0200 @@ -3,7 +3,7 @@ Copyright (C) 1995 Tinker Systems Copyright (C) 1995, 1996 Ben Wing Copyright (C) 1995 Sun Microsystems - Copyright (C) 1998 Andy Piper + Copyright (C) 1998, 1999 Andy Piper This file is part of XEmacs. @@ -24,7 +24,7 @@ /* Synched up with: Not in FSF. */ -/* Written by Ben Wing and Chuck Thompson */ +/* Written by Ben Wing and Chuck Thompson. */ #include #include "lisp.h" @@ -42,6 +42,7 @@ #include "frame.h" #include "chartab.h" #include "rangetab.h" +#include "blocktype.h" #ifdef HAVE_XPM #include @@ -56,6 +57,7 @@ Lisp_Object Qcolor_pixmap_image_instance_p; Lisp_Object Qpointer_image_instance_p; Lisp_Object Qsubwindow_image_instance_p; +Lisp_Object Qlayout_image_instance_p; Lisp_Object Qwidget_image_instance_p; Lisp_Object Qconst_glyph_variable; Lisp_Object Qmono_pixmap, Qcolor_pixmap, Qsubwindow; @@ -70,11 +72,14 @@ Lisp_Object Vimage_instance_type_list; Lisp_Object Vglyph_type_list; +int disable_animated_pixmaps; + DEFINE_IMAGE_INSTANTIATOR_FORMAT (nothing); DEFINE_IMAGE_INSTANTIATOR_FORMAT (inherit); DEFINE_IMAGE_INSTANTIATOR_FORMAT (string); DEFINE_IMAGE_INSTANTIATOR_FORMAT (formatted_string); DEFINE_IMAGE_INSTANTIATOR_FORMAT (subwindow); +DEFINE_IMAGE_INSTANTIATOR_FORMAT (text); #ifdef HAVE_WINDOW_SYSTEM DEFINE_IMAGE_INSTANTIATOR_FORMAT (xbm); @@ -122,6 +127,13 @@ static void glyph_property_was_changed (Lisp_Object glyph, Lisp_Object property, Lisp_Object locale); +static void register_ignored_expose (struct frame* f, int x, int y, int width, int height); +/* Unfortunately windows and X are different. In windows BeginPaint() + will prevent WM_PAINT messages being generated so it is unnecessary + to register exposures as they will not occur. Under X they will + always occur. */ +int hold_ignored_expose_registration; + EXFUN (Fimage_instance_type, 1); EXFUN (Fglyph_type, 1); @@ -179,13 +191,20 @@ int i; struct image_instantiator_methods* meths = decode_image_instantiator_format (format, ERROR_ME_NOT); - struct console* console = decode_console (locale); - Lisp_Object contype = console ? CONSOLE_TYPE (console) : locale; + Lisp_Object contype = Qnil; + /* mess with the locale */ + if (!NILP (locale) && SYMBOLP (locale)) + contype = locale; + else + { + struct console* console = decode_console (locale); + contype = console ? CONSOLE_TYPE (console) : locale; + } /* nothing is valid in all locales */ if (EQ (format, Qnothing)) return 1; /* reject unknown formats */ - else if (!console || !meths) + else if (NILP (contype) || !meths) return 0; for (i = 0; i < Dynarr_length (meths->consoles); i++) @@ -598,40 +617,46 @@ Lisp_Object Qimage_instancep; static Lisp_Object -mark_image_instance (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_image_instance (Lisp_Object obj) { struct Lisp_Image_Instance *i = XIMAGE_INSTANCE (obj); - markobj (i->name); + mark_object (i->name); switch (IMAGE_INSTANCE_TYPE (i)) { case IMAGE_TEXT: - markobj (IMAGE_INSTANCE_TEXT_STRING (i)); + mark_object (IMAGE_INSTANCE_TEXT_STRING (i)); break; case IMAGE_MONO_PIXMAP: case IMAGE_COLOR_PIXMAP: - markobj (IMAGE_INSTANCE_PIXMAP_FILENAME (i)); - markobj (IMAGE_INSTANCE_PIXMAP_MASK_FILENAME (i)); - markobj (IMAGE_INSTANCE_PIXMAP_HOTSPOT_X (i)); - markobj (IMAGE_INSTANCE_PIXMAP_HOTSPOT_Y (i)); - markobj (IMAGE_INSTANCE_PIXMAP_FG (i)); - markobj (IMAGE_INSTANCE_PIXMAP_BG (i)); + mark_object (IMAGE_INSTANCE_PIXMAP_FILENAME (i)); + mark_object (IMAGE_INSTANCE_PIXMAP_MASK_FILENAME (i)); + mark_object (IMAGE_INSTANCE_PIXMAP_HOTSPOT_X (i)); + mark_object (IMAGE_INSTANCE_PIXMAP_HOTSPOT_Y (i)); + mark_object (IMAGE_INSTANCE_PIXMAP_FG (i)); + mark_object (IMAGE_INSTANCE_PIXMAP_BG (i)); break; case IMAGE_WIDGET: - markobj (IMAGE_INSTANCE_WIDGET_TYPE (i)); - markobj (IMAGE_INSTANCE_WIDGET_PROPS (i)); - markobj (IMAGE_INSTANCE_WIDGET_FACE (i)); - markobj (IMAGE_INSTANCE_WIDGET_ITEM (i)); + mark_object (IMAGE_INSTANCE_WIDGET_TYPE (i)); + mark_object (IMAGE_INSTANCE_WIDGET_PROPS (i)); + mark_object (IMAGE_INSTANCE_WIDGET_FACE (i)); + mark_object (IMAGE_INSTANCE_WIDGET_ITEMS (i)); case IMAGE_SUBWINDOW: - markobj (IMAGE_INSTANCE_SUBWINDOW_FRAME (i)); + mark_object (IMAGE_INSTANCE_SUBWINDOW_FRAME (i)); + break; + + case IMAGE_LAYOUT: + mark_object (IMAGE_INSTANCE_LAYOUT_CHILDREN (i)); + mark_object (IMAGE_INSTANCE_LAYOUT_BORDER (i)); + mark_object (IMAGE_INSTANCE_SUBWINDOW_FRAME (i)); break; default: break; } - MAYBE_DEVMETH (XDEVICE (i->device), mark_image_instance, (i, markobj)); + MAYBE_DEVMETH (XDEVICE (i->device), mark_image_instance, (i)); return i->device; } @@ -748,6 +773,7 @@ print_internal (IMAGE_INSTANCE_WIDGET_TEXT (ii), printcharfun, 0); case IMAGE_SUBWINDOW: + case IMAGE_LAYOUT: sprintf (buf, " %dx%d", IMAGE_INSTANCE_SUBWINDOW_WIDTH (ii), IMAGE_INSTANCE_SUBWINDOW_HEIGHT (ii)); write_c_string (buf, printcharfun); @@ -799,7 +825,7 @@ || IMAGE_INSTANCE_TYPE (i) == IMAGE_SUBWINDOW) { - MARK_FRAME_GLYPHS_CHANGED + MARK_FRAME_SUBWINDOWS_CHANGED (XFRAME (IMAGE_INSTANCE_SUBWINDOW_FRAME (i))); } @@ -843,6 +869,8 @@ IMAGE_INSTANCE_PIXMAP_HEIGHT (i2) && IMAGE_INSTANCE_PIXMAP_DEPTH (i1) == IMAGE_INSTANCE_PIXMAP_DEPTH (i2) && + IMAGE_INSTANCE_PIXMAP_SLICE (i1) == + IMAGE_INSTANCE_PIXMAP_SLICE (i2) && EQ (IMAGE_INSTANCE_PIXMAP_HOTSPOT_X (i1), IMAGE_INSTANCE_PIXMAP_HOTSPOT_X (i2)) && EQ (IMAGE_INSTANCE_PIXMAP_HOTSPOT_Y (i1), @@ -859,14 +887,24 @@ case IMAGE_WIDGET: if (!(EQ (IMAGE_INSTANCE_WIDGET_TYPE (i1), IMAGE_INSTANCE_WIDGET_TYPE (i2)) - && internal_equal (IMAGE_INSTANCE_WIDGET_ITEM (i1), - IMAGE_INSTANCE_WIDGET_ITEM (i2), + && internal_equal (IMAGE_INSTANCE_WIDGET_ITEMS (i1), + IMAGE_INSTANCE_WIDGET_ITEMS (i2), depth + 1) && internal_equal (IMAGE_INSTANCE_WIDGET_PROPS (i1), IMAGE_INSTANCE_WIDGET_PROPS (i2), depth + 1) )) return 0; + case IMAGE_LAYOUT: + if (IMAGE_INSTANCE_TYPE (i1) == IMAGE_LAYOUT + && + !(EQ (IMAGE_INSTANCE_LAYOUT_BORDER (i1), + IMAGE_INSTANCE_LAYOUT_BORDER (i2)) + && + internal_equal (IMAGE_INSTANCE_LAYOUT_CHILDREN (i1), + IMAGE_INSTANCE_LAYOUT_CHILDREN (i2), + depth + 1))) + return 0; case IMAGE_SUBWINDOW: if (!(IMAGE_INSTANCE_SUBWINDOW_WIDTH (i1) == IMAGE_INSTANCE_SUBWINDOW_WIDTH (i2) && @@ -904,9 +942,10 @@ case IMAGE_MONO_PIXMAP: case IMAGE_COLOR_PIXMAP: case IMAGE_POINTER: - hash = HASH5 (hash, IMAGE_INSTANCE_PIXMAP_WIDTH (i), + hash = HASH6 (hash, IMAGE_INSTANCE_PIXMAP_WIDTH (i), IMAGE_INSTANCE_PIXMAP_HEIGHT (i), IMAGE_INSTANCE_PIXMAP_DEPTH (i), + IMAGE_INSTANCE_PIXMAP_SLICE (i), internal_hash (IMAGE_INSTANCE_PIXMAP_FILENAME (i), depth + 1)); break; @@ -915,7 +954,13 @@ hash = HASH4 (hash, internal_hash (IMAGE_INSTANCE_WIDGET_TYPE (i), depth + 1), internal_hash (IMAGE_INSTANCE_WIDGET_PROPS (i), depth + 1), - internal_hash (IMAGE_INSTANCE_WIDGET_ITEM (i), depth + 1)); + internal_hash (IMAGE_INSTANCE_WIDGET_ITEMS (i), depth + 1)); + case IMAGE_LAYOUT: + if (IMAGE_INSTANCE_TYPE (i) == IMAGE_LAYOUT) + hash = HASH3 (hash, + internal_hash (IMAGE_INSTANCE_LAYOUT_BORDER (i), depth + 1), + internal_hash (IMAGE_INSTANCE_LAYOUT_CHILDREN (i), + depth + 1)); case IMAGE_SUBWINDOW: hash = HASH4 (hash, IMAGE_INSTANCE_SUBWINDOW_WIDTH (i), IMAGE_INSTANCE_SUBWINDOW_HEIGHT (i), @@ -947,6 +992,8 @@ lp->device = device; lp->type = IMAGE_NOTHING; lp->name = Qnil; + lp->x_offset = 0; + lp->y_offset = 0; XSETIMAGE_INSTANCE (val, lp); return val; } @@ -964,6 +1011,7 @@ if (EQ (type, Qpointer)) return IMAGE_POINTER; if (EQ (type, Qsubwindow)) return IMAGE_SUBWINDOW; if (EQ (type, Qwidget)) return IMAGE_WIDGET; + if (EQ (type, Qlayout)) return IMAGE_LAYOUT; maybe_signal_simple_error ("Invalid image-instance type", type, Qimage, errb); @@ -983,6 +1031,7 @@ case IMAGE_POINTER: return Qpointer; case IMAGE_SUBWINDOW: return Qsubwindow; case IMAGE_WIDGET: return Qwidget; + case IMAGE_LAYOUT: return Qlayout; default: abort (); } @@ -995,7 +1044,7 @@ { /* This depends on the fact that enums are assigned consecutive integers starting at 0. (Remember that IMAGE_UNKNOWN is the - first enum.) I'm fairly sure this behavior in ANSI-mandated, + first enum.) I'm fairly sure this behavior is ANSI-mandated, so there should be no portability problems here. */ return (1 << ((int) (type) - 1)); } @@ -1166,7 +1215,9 @@ 'subwindow A child window that is treated as an image. This allows (e.g.) another program to be responsible for drawing into the window. - Not currently implemented. +'widget + A child window that contains a window-system widget, e.g. a push + button. The DEST-TYPES list is unordered. If multiple destination types are possible for a given instantiator, the "most natural" type @@ -1188,7 +1239,7 @@ NO-ERROR controls what happens when the image cannot be generated. If nil, an error message is generated. If t, no messages are generated and this function returns nil. If anything else, a warning -message is generated and this function returns nil. +message is generated and this function returns nil. */ (data, device, dest_types, no_error)) { @@ -1302,18 +1353,30 @@ !UNBOUNDP (ret = IIFORMAT_METH (meths, set_property, (image_instance, prop, val)))) { - return ret; + val = ret; } - /* ... then format specific methods ... */ - meths = decode_device_ii_format (Qnil, type, ERROR_ME_NOT); - if (meths && HAS_IIFORMAT_METH_P (meths, set_property) - && - !UNBOUNDP (ret = - IIFORMAT_METH (meths, set_property, (image_instance, prop, val)))) + else { - return ret; + /* ... then format specific methods ... */ + meths = decode_device_ii_format (Qnil, type, ERROR_ME_NOT); + if (meths && HAS_IIFORMAT_METH_P (meths, set_property) + && + !UNBOUNDP (ret = + IIFORMAT_METH (meths, set_property, (image_instance, prop, val)))) + { + val = ret; + } + else + { + val = Qnil; + } } + /* Make sure the image instance gets redisplayed. */ + MARK_IMAGE_INSTANCE_CHANGED (ii); + MARK_SUBWINDOWS_STATE_CHANGED; + MARK_GLYPHS_CHANGED; + return val; } @@ -1391,6 +1454,7 @@ case IMAGE_SUBWINDOW: case IMAGE_WIDGET: + case IMAGE_LAYOUT: return make_int (XIMAGE_INSTANCE_SUBWINDOW_HEIGHT (image_instance)); default: @@ -1414,6 +1478,7 @@ case IMAGE_SUBWINDOW: case IMAGE_WIDGET: + case IMAGE_LAYOUT: return make_int (XIMAGE_INSTANCE_SUBWINDOW_WIDTH (image_instance)); default: @@ -1670,6 +1735,23 @@ incompatible_image_types (instantiator, dest_mask, IMAGE_TEXT_MASK); } +/* set the properties of a string */ +static Lisp_Object +text_set_property (Lisp_Object image_instance, Lisp_Object prop, + Lisp_Object val) +{ + struct Lisp_Image_Instance *ii = XIMAGE_INSTANCE (image_instance); + + if (EQ (prop, Q_data)) + { + CHECK_STRING (val); + IMAGE_INSTANCE_TEXT_STRING (ii) = val; + + return Qt; + } + return Qunbound; +} + /**************************************************************************** * formatted-string * @@ -2334,12 +2416,12 @@ } static void -image_mark (Lisp_Object obj, void (*markobj) (Lisp_Object)) +image_mark (Lisp_Object obj) { struct Lisp_Specifier *image = XIMAGE_SPECIFIER (obj); - markobj (IMAGE_SPECIFIER_ATTACHEE (image)); - markobj (IMAGE_SPECIFIER_ATTACHEE_PROPERTY (image)); + mark_object (IMAGE_SPECIFIER_ATTACHEE (image)); + mark_object (IMAGE_SPECIFIER_ATTACHEE_PROPERTY (image)); } static Lisp_Object @@ -2733,9 +2815,21 @@ Currently can only be instanced as `pointer', although this should probably be fixed.) 'subwindow - (An embedded X window; not currently implemented.) -'widget - (A widget control, for instance text field or radio button.) + (An embedded windowing system window.) +'edit-field + (A text editing widget glyph.) +'button + (A button widget glyph; either a push button, radio button or toggle button.) +'tab-control + (A tab widget glyph; a series of user selectable tabs.) +'progress-gauge + (A sliding widget glyph, for showing progress.) +'combo-box + (A drop list of selectable items in a widget glyph, for editing text.) +'label + (A static, text-only, widget glyph; for displaying text.) +'tree-view + (A folding widget glyph.) 'autodetect (XEmacs tries to guess what format the data is in. If X support exists, the data string will be checked to see if it names a filename. @@ -2797,7 +2891,14 @@ object). If this is not specified, the contents of `xpm-color-symbols' are used to generate the alist.) :face - (Only for `inherit'. This specifies the face to inherit from.) + (Only for `inherit'. This specifies the face to inherit from. + For widget glyphs this also specifies the face to use for + display. It defaults to gui-element-face.) + +Keywords accepted as menu item specs are also accepted by widget +glyphs. These are `:selected', `:active', `:suffix', `:keys', +`:style', `:filter', `:config', `:included', `:key-sequence', +`:accelerator', `:label' and `:callback'. If instead of a vector, the instantiator is a string, it will be converted into a vector by looking it up according to the specs in the @@ -2825,14 +2926,14 @@ ****************************************************************************/ static Lisp_Object -mark_glyph (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_glyph (Lisp_Object obj) { struct Lisp_Glyph *glyph = XGLYPH (obj); - markobj (glyph->image); - markobj (glyph->contrib_p); - markobj (glyph->baseline); - markobj (glyph->face); + mark_object (glyph->image); + mark_object (glyph->contrib_p); + mark_object (glyph->baseline); + mark_object (glyph->face); return glyph->plist; } @@ -2902,9 +3003,9 @@ static int glyph_putprop (Lisp_Object obj, Lisp_Object prop, Lisp_Object value) { - if ((EQ (prop, Qimage)) || - (EQ (prop, Qcontrib_p)) || - (EQ (prop, Qbaseline))) + if (EQ (prop, Qimage) || + EQ (prop, Qcontrib_p) || + EQ (prop, Qbaseline)) return 0; if (EQ (prop, Qface)) @@ -2920,9 +3021,9 @@ static int glyph_remprop (Lisp_Object obj, Lisp_Object prop) { - if ((EQ (prop, Qimage)) || - (EQ (prop, Qcontrib_p)) || - (EQ (prop, Qbaseline))) + if (EQ (prop, Qimage) || + EQ (prop, Qcontrib_p) || + EQ (prop, Qbaseline)) return -1; if (EQ (prop, Qface)) @@ -2972,13 +3073,15 @@ g->type = type; g->image = Fmake_specifier (Qimage); /* This function can GC */ + g->dirty = 0; switch (g->type) { case GLYPH_BUFFER: XIMAGE_SPECIFIER_ALLOWED (g->image) = IMAGE_NOTHING_MASK | IMAGE_TEXT_MASK | IMAGE_MONO_PIXMAP_MASK | IMAGE_COLOR_PIXMAP_MASK - | IMAGE_SUBWINDOW_MASK | IMAGE_WIDGET_MASK; + | IMAGE_SUBWINDOW_MASK | IMAGE_WIDGET_MASK + | IMAGE_LAYOUT_MASK; break; case GLYPH_POINTER: XIMAGE_SPECIFIER_ALLOWED (g->image) = @@ -3127,18 +3230,16 @@ the given FACE, unless a face is defined by the glyph itself. ****************************************************************************/ unsigned short -glyph_width (Lisp_Object glyph, Lisp_Object frame_face, +glyph_width (Lisp_Object glyph_or_image, Lisp_Object frame_face, face_index window_findex, Lisp_Object window) { - Lisp_Object instance; + Lisp_Object instance = glyph_or_image; Lisp_Object frame = XWINDOW (window)->frame; /* #### We somehow need to distinguish between the user causing this error condition and a bug causing it. */ - if (!GLYPHP (glyph)) - return 0; - else - instance = glyph_image_instance (glyph, window, ERROR_ME_NOT, 1); + if (GLYPHP (glyph_or_image)) + instance = glyph_image_instance (glyph_or_image, window, ERROR_ME_NOT, 1); if (!IMAGE_INSTANCEP (instance)) return 0; @@ -3148,7 +3249,10 @@ case IMAGE_TEXT: { Lisp_Object str = XIMAGE_INSTANCE_TEXT_STRING (instance); - Lisp_Object private_face = XGLYPH_FACE(glyph); + Lisp_Object private_face = Qnil; + + if (GLYPHP (glyph_or_image)) + private_face = XGLYPH_FACE(glyph_or_image); if (!NILP (private_face)) return redisplay_frame_text_width_string (XFRAME (frame), @@ -3175,6 +3279,7 @@ case IMAGE_SUBWINDOW: case IMAGE_WIDGET: + case IMAGE_LAYOUT: return XIMAGE_INSTANCE_SUBWINDOW_WIDTH (instance); default: @@ -3213,17 +3318,15 @@ } static unsigned short -glyph_height_internal (Lisp_Object glyph, Lisp_Object frame_face, +glyph_height_internal (Lisp_Object glyph_or_image, Lisp_Object frame_face, face_index window_findex, Lisp_Object window, int function) { - Lisp_Object instance; + Lisp_Object instance = glyph_or_image; Lisp_Object frame = XWINDOW (window)->frame; - if (!GLYPHP (glyph)) - return 0; - else - instance = glyph_image_instance (glyph, window, ERROR_ME_NOT, 1); + if (GLYPHP (glyph_or_image)) + instance = glyph_image_instance (glyph_or_image, window, ERROR_ME_NOT, 1); if (!IMAGE_INSTANCEP (instance)) return 0; @@ -3279,6 +3382,7 @@ case IMAGE_SUBWINDOW: case IMAGE_WIDGET: + case IMAGE_LAYOUT: /* #### Ugh ugh ugh -- temporary crap */ if (function == RETURN_ASCENT || function == RETURN_HEIGHT) return XIMAGE_INSTANCE_SUBWINDOW_HEIGHT (instance); @@ -3360,6 +3464,35 @@ #undef RETURN_DESCENT #undef RETURN_HEIGHT +static unsigned int +glyph_dirty_p (Lisp_Object glyph_or_image, Lisp_Object window) +{ + Lisp_Object instance = glyph_or_image; + + if (GLYPHP (glyph_or_image)) + instance = glyph_image_instance (glyph_or_image, window, ERROR_ME_NOT, 1); + + return XIMAGE_INSTANCE_DIRTYP (instance); +} + +static void +set_glyph_dirty_p (Lisp_Object glyph_or_image, Lisp_Object window, int dirty) +{ + Lisp_Object instance = glyph_or_image; + + if (!NILP (glyph_or_image)) + { + if (GLYPHP (glyph_or_image)) + { + instance = glyph_image_instance (glyph_or_image, window, + ERROR_ME_NOT, 1); + XGLYPH_DIRTYP (glyph_or_image) = dirty; + } + + XIMAGE_INSTANCE_DIRTYP (instance) = dirty; + } +} + /* #### do we need to cache this info to speed things up? */ Lisp_Object @@ -3422,12 +3555,10 @@ /* #### All of this is 95% copied from face cachels. Consider consolidating. - #### We need to add a dirty flag to the glyphs. */ void -mark_glyph_cachels (glyph_cachel_dynarr *elements, - void (*markobj) (Lisp_Object)) +mark_glyph_cachels (glyph_cachel_dynarr *elements) { int elt; @@ -3437,7 +3568,7 @@ for (elt = 0; elt < Dynarr_length (elements); elt++) { struct glyph_cachel *cachel = Dynarr_atp (elements, elt); - markobj (cachel->glyph); + mark_object (cachel->glyph); } } @@ -3445,19 +3576,21 @@ update_glyph_cachel_data (struct window *w, Lisp_Object glyph, struct glyph_cachel *cachel) { - /* #### This should be || !cachel->updated */ - if (NILP (cachel->glyph) || !EQ (cachel->glyph, glyph)) + if (!cachel->updated || NILP (cachel->glyph) || !EQ (cachel->glyph, glyph) + || XGLYPH_DIRTYP (cachel->glyph)) { - Lisp_Object window; + Lisp_Object window, instance; XSETWINDOW (window, w); - /* #### This could be sped up if we redid things to grab the glyph - instantiation and passed it to the size functions. */ cachel->glyph = glyph; - cachel->width = glyph_width (glyph, Qnil, DEFAULT_INDEX, window); - cachel->ascent = glyph_ascent (glyph, Qnil, DEFAULT_INDEX, window); - cachel->descent = glyph_descent (glyph, Qnil, DEFAULT_INDEX, window); + /* Speed things up slightly by grabbing the glyph instantiation + and passing it to the size functions. */ + instance = glyph_image_instance (glyph, window, ERROR_ME_NOT, 1); + cachel->dirty = XGLYPH_DIRTYP (glyph) = glyph_dirty_p (glyph, window); + cachel->width = glyph_width (instance, Qnil, DEFAULT_INDEX, window); + cachel->ascent = glyph_ascent (instance, Qnil, DEFAULT_INDEX, window); + cachel->descent = glyph_descent (instance, Qnil, DEFAULT_INDEX, window); } cachel->updated = 1; @@ -3475,7 +3608,7 @@ Dynarr_add (w->glyph_cachels, new_cachel); } -static glyph_index +glyph_index get_glyph_cachel_index (struct window *w, Lisp_Object glyph) { int elt; @@ -3490,8 +3623,7 @@ if (EQ (cachel->glyph, glyph) && !NILP (glyph)) { - if (!cachel->updated) - update_glyph_cachel_data (w, glyph, cachel); + update_glyph_cachel_data (w, glyph, cachel); return elt; } } @@ -3534,7 +3666,24 @@ #undef FROB for (elt = 0; elt < Dynarr_length (w->glyph_cachels); elt++) - Dynarr_atp (w->glyph_cachels, elt)->updated = 0; + { + Dynarr_atp (w->glyph_cachels, elt)->updated = 0; + } +} + +/* Unset the dirty bit on all the glyph cachels that have it. */ +void +mark_glyph_cachels_as_clean (struct window* w) +{ + int elt; + Lisp_Object window; + XSETWINDOW (window, w); + for (elt = 0; elt < Dynarr_length (w->glyph_cachels); elt++) + { + struct glyph_cachel *cachel = Dynarr_atp (w->glyph_cachels, elt); + cachel->dirty = 0; + set_glyph_dirty_p (cachel->glyph, window, 0); + } } #ifdef MEMORY_USAGE_STATS @@ -3568,7 +3717,7 @@ obscuring an area that we want to clear. We need to be able to flip through this quickly so a hashtable is not suitable hence the subwindow_cachels. The question is should we just not mark - instances in the subwindow_cachelsnor should we try and invalidate + instances in the subwindow_cachels or should we try and invalidate the cache at suitable points in redisplay? If we don't invalidate the cache it will fill up with crud that will only get removed when the frame is deleted. So invalidation is good, the question is when @@ -3576,8 +3725,7 @@ MARK_SUBWINDOWS_CHANGED when a subwindow gets deleted. */ void -mark_subwindow_cachels (subwindow_cachel_dynarr *elements, - void (*markobj) (Lisp_Object)) +mark_subwindow_cachels (subwindow_cachel_dynarr *elements) { int elt; @@ -3587,7 +3735,7 @@ for (elt = 0; elt < Dynarr_length (elements); elt++) { struct subwindow_cachel *cachel = Dynarr_atp (elements, elt); - markobj (cachel->subwindow); + mark_object (cachel->subwindow); } } @@ -3595,13 +3743,9 @@ update_subwindow_cachel_data (struct frame *f, Lisp_Object subwindow, struct subwindow_cachel *cachel) { - if (NILP (cachel->subwindow) || !EQ (cachel->subwindow, subwindow)) - { - cachel->subwindow = subwindow; - cachel->width = XIMAGE_INSTANCE_SUBWINDOW_WIDTH (subwindow); - cachel->height = XIMAGE_INSTANCE_SUBWINDOW_HEIGHT (subwindow); - } - + cachel->subwindow = subwindow; + cachel->width = XIMAGE_INSTANCE_SUBWINDOW_WIDTH (subwindow); + cachel->height = XIMAGE_INSTANCE_SUBWINDOW_HEIGHT (subwindow); cachel->updated = 1; } @@ -3646,6 +3790,29 @@ return elt; } +static void +update_subwindow_cachel (Lisp_Object subwindow) +{ + struct frame* f; + int elt; + + if (NILP (subwindow)) + return; + + f = XFRAME ( XIMAGE_INSTANCE_SUBWINDOW_FRAME (subwindow)); + + for (elt = 0; elt < Dynarr_length (f->subwindow_cachels); elt++) + { + struct subwindow_cachel *cachel = + Dynarr_atp (f->subwindow_cachels, elt); + + if (EQ (cachel->subwindow, subwindow) && !NILP (subwindow)) + { + update_subwindow_cachel_data (f, subwindow, cachel); + } + } +} + /* redisplay in general assumes that drawing something will erase what was there before. unfortunately this does not apply to subwindows that need to be specifically unmapped in order to @@ -3662,8 +3829,10 @@ if (!NILP (cachel->subwindow) && cachel->being_displayed) { - struct Lisp_Image_Instance* ii = XIMAGE_INSTANCE (cachel->subwindow); - MAYBE_DEVMETH (XDEVICE (f->device), unmap_subwindow, (ii)); + cachel->updated = 1; + /* #### This is not optimal as update_subwindow will search + the cachels for ourselves as well. We could easily optimize. */ + unmap_subwindow (cachel->subwindow); } } Dynarr_reset (f->subwindow_cachels); @@ -3678,6 +3847,119 @@ Dynarr_atp (f->subwindow_cachels, elt)->updated = 0; } + + +/***************************************************************************** + * subwindow exposure ignorance * + *****************************************************************************/ +/* when we unmap subwindows the associated window system will generate + expose events. This we do not want as redisplay already copes with + the repainting necessary. Worse, we can get in an endless cycle of + redisplay if we are not careful. Thus we keep a per-frame list of + expose events that are going to come and ignore them as + required. */ + +struct expose_ignore_blocktype +{ + Blocktype_declare (struct expose_ignore); +} *the_expose_ignore_blocktype; + +int +check_for_ignored_expose (struct frame* f, int x, int y, int width, int height) +{ + struct expose_ignore *ei, *prev; + /* the ignore list is FIFO so we should generally get a match with + the first element in the list */ + for (ei = f->subwindow_exposures, prev = 0; ei; ei = ei->next) + { + /* Checking for exact matches just isn't good enough as we + mighte get exposures for partially obscure subwindows, thus + we have to check for overlaps. Being conservative we will + check for exposures wholly contained by the subwindow, this + might give us what we want.*/ + if (ei->x <= x && ei->y <= y + && ei->x + ei->width >= x + width + && ei->y + ei->height >= y + height) + { +#ifdef DEBUG_WIDGETS + stderr_out ("ignored %d+%d, %dx%d for exposure %d+%d, %dx%d\n", + x, y, width, height, ei->x, ei->y, ei->width, ei->height); +#endif + if (!prev) + f->subwindow_exposures = ei->next; + else + prev->next = ei->next; + + if (ei == f->subwindow_exposures_tail) + f->subwindow_exposures_tail = prev; + + Blocktype_free (the_expose_ignore_blocktype, ei); + return 1; + } + prev = ei; + } + return 0; +} + +static void +register_ignored_expose (struct frame* f, int x, int y, int width, int height) +{ + if (!hold_ignored_expose_registration) + { + struct expose_ignore *ei; + + ei = Blocktype_alloc (the_expose_ignore_blocktype); + + ei->next = NULL; + ei->x = x; + ei->y = y; + ei->width = width; + ei->height = height; + + /* we have to add the exposure to the end of the list, since we + want to check the oldest events first. for speed we keep a record + of the end so that we can add right to it. */ + if (f->subwindow_exposures_tail) + { + f->subwindow_exposures_tail->next = ei; + } + if (!f->subwindow_exposures) + { + f->subwindow_exposures = ei; + } + f->subwindow_exposures_tail = ei; + } +} + +/**************************************************************************** + find_matching_subwindow + + See if there is a subwindow that completely encloses the requested + area. + ****************************************************************************/ +int find_matching_subwindow (struct frame* f, int x, int y, int width, int height) +{ + int elt; + + for (elt = 0; elt < Dynarr_length (f->subwindow_cachels); elt++) + { + struct subwindow_cachel *cachel = + Dynarr_atp (f->subwindow_cachels, elt); + + if (cachel->being_displayed + && + cachel->x <= x && cachel->y <= y + && + cachel->x + cachel->width >= x + width + && + cachel->y + cachel->height >= y + height) + { + return 1; + } + } + return 0; +} + /***************************************************************************** * subwindow functions * @@ -3702,7 +3984,7 @@ { int elt; - if (f->subwindows_changed || f->glyphs_changed) + if (f->subwindows_changed || f->subwindows_state_changed || f->faces_changed) for (elt = 0; elt < Dynarr_length (f->subwindow_cachels); elt++) { struct subwindow_cachel *cachel = @@ -3729,11 +4011,15 @@ || NILP (IMAGE_INSTANCE_SUBWINDOW_FRAME (ii))) return; - +#ifdef DEBUG_WIDGETS + stderr_out ("unmapping subwindow %d\n", IMAGE_INSTANCE_SUBWINDOW_ID (ii)); +#endif f = XFRAME (IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); elt = get_subwindow_cachel_index (f, subwindow); cachel = Dynarr_atp (f->subwindow_cachels, elt); + /* make sure we don't get expose events */ + register_ignored_expose (f, cachel->x, cachel->y, cachel->width, cachel->height); cachel->x = -1; cachel->y = -1; cachel->being_displayed = 0; @@ -3743,7 +4029,8 @@ } /* show a subwindow in its frame */ -void map_subwindow (Lisp_Object subwindow, int x, int y) +void map_subwindow (Lisp_Object subwindow, int x, int y, + struct display_glyph_area *dga) { struct Lisp_Image_Instance* ii = XIMAGE_INSTANCE (subwindow); int elt; @@ -3757,15 +4044,22 @@ NILP (IMAGE_INSTANCE_SUBWINDOW_FRAME (ii))) return; +#ifdef DEBUG_WIDGETS + stderr_out ("mapping subwindow %d, %dx%d@%d+%d\n", + IMAGE_INSTANCE_SUBWINDOW_ID (ii), + dga->width, dga->height, x, y); +#endif f = XFRAME (IMAGE_INSTANCE_SUBWINDOW_FRAME (ii)); IMAGE_INSTANCE_SUBWINDOW_DISPLAYEDP (ii) = 1; elt = get_subwindow_cachel_index (f, subwindow); cachel = Dynarr_atp (f->subwindow_cachels, elt); cachel->x = x; cachel->y = y; + cachel->width = dga->width; + cachel->height = dga->height; cachel->being_displayed = 1; - MAYBE_DEVMETH (XDEVICE (ii->device), map_subwindow, (ii, x, y)); + MAYBE_DEVMETH (XDEVICE (ii->device), map_subwindow, (ii, x, y, dga)); } static int @@ -3794,7 +4088,6 @@ ii->data = 0; IMAGE_INSTANCE_SUBWINDOW_ID (ii) = 0; - IMAGE_INSTANCE_SUBWINDOW_FRAME (ii) = Qnil; IMAGE_INSTANCE_SUBWINDOW_DISPLAYEDP (ii) = 0; IMAGE_INSTANCE_SUBWINDOW_FRAME (ii) = frame; @@ -3836,7 +4129,7 @@ (subwindow)) { CHECK_SUBWINDOW_IMAGE_INSTANCE (subwindow); - return make_int ((int) (XIMAGE_INSTANCE_SUBWINDOW_ID (subwindow))); + return make_int ((int) XIMAGE_INSTANCE_SUBWINDOW_ID (subwindow)); } DEFUN ("resize-subwindow", Fresize_subwindow, 1, 3, 0, /* @@ -3866,6 +4159,9 @@ XIMAGE_INSTANCE_SUBWINDOW_HEIGHT (subwindow) = newh; XIMAGE_INSTANCE_SUBWINDOW_WIDTH (subwindow) = neww; + /* need to update the cachels as redisplay will not do this */ + update_subwindow_cachel (subwindow); + return subwindow; } @@ -3875,9 +4171,9 @@ (subwindow)) { CHECK_SUBWINDOW_IMAGE_INSTANCE (subwindow); - +#if 0 map_subwindow (subwindow, 0, 0); - +#endif return subwindow; } @@ -3963,6 +4259,80 @@ abort (); } } + +/***************************************************************************** + * timeouts for animated glyphs * + *****************************************************************************/ +static Lisp_Object Qglyph_animated_timeout_handler; + +DEFUN ("glyph-animated-timeout-handler", Fglyph_animated_timeout_handler, 1, 1, 0, /* +Callback function for updating animated images. +Don't use this. +*/ + (arg)) +{ + CHECK_WEAK_LIST (arg); + + if (!NILP (XWEAK_LIST_LIST (arg)) && !NILP (XCAR (XWEAK_LIST_LIST (arg)))) + { + Lisp_Object value = XCAR (XWEAK_LIST_LIST (arg)); + + if (IMAGE_INSTANCEP (value)) + { + struct Lisp_Image_Instance* ii = XIMAGE_INSTANCE (value); + + if (COLOR_PIXMAP_IMAGE_INSTANCEP (value) + && + IMAGE_INSTANCE_PIXMAP_MAXSLICE (ii) > 1 + && + !disable_animated_pixmaps) + { + /* Increment the index of the image slice we are currently + viewing. */ + IMAGE_INSTANCE_PIXMAP_SLICE (ii) = + (IMAGE_INSTANCE_PIXMAP_SLICE (ii) + 1) + % IMAGE_INSTANCE_PIXMAP_MAXSLICE (ii); + /* We might need to kick redisplay at this point - but we + also might not. */ + MARK_DEVICE_FRAMES_GLYPHS_CHANGED + (XDEVICE (IMAGE_INSTANCE_DEVICE (ii))); + IMAGE_INSTANCE_DIRTYP (ii) = 1; + } + } + } + return Qnil; +} + +Lisp_Object add_glyph_animated_timeout (EMACS_INT tickms, Lisp_Object image) +{ + Lisp_Object ret = Qnil; + + if (tickms > 0 && IMAGE_INSTANCEP (image)) + { + double ms = ((double)tickms) / 1000.0; + struct gcpro gcpro1; + Lisp_Object holder = make_weak_list (WEAK_LIST_SIMPLE); + + GCPRO1 (holder); + XWEAK_LIST_LIST (holder) = Fcons (image, Qnil); + + ret = Fadd_timeout (make_float (ms), + Qglyph_animated_timeout_handler, + holder, make_float (ms)); + + UNGCPRO; + } + return ret; +} + +void disable_glyph_animated_timeout (int i) +{ + Lisp_Object id; + XSETINT (id, i); + + Fdisable_timeout (id); +} + /***************************************************************************** * initialization * @@ -4011,6 +4381,7 @@ defsymbol (&Qpointer_image_instance_p, "pointer-image-instance-p"); defsymbol (&Qwidget_image_instance_p, "widget-image-instance-p"); defsymbol (&Qsubwindow_image_instance_p, "subwindow-image-instance-p"); + defsymbol (&Qlayout_image_instance_p, "layout-image-instance-p"); DEFSUBR (Fmake_image_instance); DEFSUBR (Fimage_instance_p); @@ -4069,6 +4440,12 @@ /* Qbuffer defined in general.c. */ /* Qpointer defined above */ + /* Unfortunately, timeout handlers must be lisp functions. This is + for animated glyphs. */ + defsymbol (&Qglyph_animated_timeout_handler, + "glyph-animated-timeout-handler"); + DEFSUBR (Fglyph_animated_timeout_handler); + /* Errors */ deferror (&Qimage_conversion_error, "image-conversion-error", @@ -4076,6 +4453,11 @@ } +static const struct lrecord_description image_specifier_description[] = { + { XD_LISP_OBJECT, specifier_data_offset + offsetof(struct image_specifier, attachee), 2 }, + { XD_END } +}; + void specifier_type_create_image (void) { @@ -4092,6 +4474,66 @@ } void +reinit_specifier_type_create_image (void) +{ + REINITIALIZE_SPECIFIER_TYPE (image); +} + + +static const struct lrecord_description iike_description_1[] = { + { XD_LISP_OBJECT, offsetof(ii_keyword_entry, keyword), 1 }, + { XD_END } +}; + +static const struct struct_description iike_description = { + sizeof(ii_keyword_entry), + iike_description_1 +}; + +static const struct lrecord_description iiked_description_1[] = { + XD_DYNARR_DESC(ii_keyword_entry_dynarr, &iike_description), + { XD_END } +}; + +static const struct struct_description iiked_description = { + sizeof(ii_keyword_entry_dynarr), + iiked_description_1 +}; + +static const struct lrecord_description iife_description_1[] = { + { XD_LISP_OBJECT, offsetof(image_instantiator_format_entry, symbol), 2 }, + { XD_STRUCT_PTR, offsetof(image_instantiator_format_entry, meths), 1, &iim_description }, + { XD_END } +}; + +static const struct struct_description iife_description = { + sizeof(image_instantiator_format_entry), + iife_description_1 +}; + +static const struct lrecord_description iifed_description_1[] = { + XD_DYNARR_DESC(image_instantiator_format_entry_dynarr, &iife_description), + { XD_END } +}; + +static const struct struct_description iifed_description = { + sizeof(image_instantiator_format_entry_dynarr), + iifed_description_1 +}; + +static const struct lrecord_description iim_description_1[] = { + { XD_LISP_OBJECT, offsetof(struct image_instantiator_methods, symbol), 2 }, + { XD_STRUCT_PTR, offsetof(struct image_instantiator_methods, keywords), 1, &iiked_description }, + { XD_STRUCT_PTR, offsetof(struct image_instantiator_methods, consoles), 1, &cted_description }, + { XD_END } +}; + +const struct struct_description iim_description = { + sizeof(struct image_instantiator_methods), + iim_description_1 +}; + +void image_instantiator_format_create (void) { /* image instantiators */ @@ -4102,6 +4544,8 @@ Vimage_instantiator_format_list = Qnil; staticpro (&Vimage_instantiator_format_list); + dumpstruct (&the_image_instantiator_format_entry_dynarr, &iifed_description); + INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (nothing, "nothing"); IIFORMAT_HAS_METHOD (nothing, possible_dest_types); @@ -4123,6 +4567,9 @@ IIFORMAT_HAS_METHOD (string, instantiate); IIFORMAT_VALID_KEYWORD (string, Q_data, check_valid_string); + /* Do this so we can set strings. */ + INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (text, "text"); + IIFORMAT_HAS_METHOD (text, set_property); INITIALIZE_IMAGE_INSTANTIATOR_FORMAT (formatted_string, "formatted-string"); @@ -4184,8 +4631,20 @@ } void +reinit_vars_of_glyphs (void) +{ + the_expose_ignore_blocktype = + Blocktype_new (struct expose_ignore_blocktype); + + hold_ignored_expose_registration = 0; +} + + +void vars_of_glyphs (void) { + reinit_vars_of_glyphs (); + Vthe_nothing_vector = vector1 (Qnothing); staticpro (&Vthe_nothing_vector); @@ -4251,6 +4710,12 @@ #ifdef HAVE_XFACE Fprovide (Qxface); #endif + + DEFVAR_BOOL ("disable-animated-pixmaps", &disable_animated_pixmaps /* +Whether animated pixmaps should be animated. +Default is t. +*/); + disable_animated_pixmaps = 0; } void diff -r 28d9c139be4c -r 11054d720c21 src/glyphs.h --- a/src/glyphs.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/glyphs.h Mon Aug 13 11:26:11 2007 +0200 @@ -56,8 +56,11 @@ inherit mono-pixmap autodetect mono-pixmap, color-pixmap, pointer, text button widget - edit widget - combo widget + edit-field widget + combo -box widget + progress-gauge widget + tab-control widget + tree-view widget scrollbar widget static widget */ @@ -78,6 +81,8 @@ Dynarr_declare (ii_keyword_entry); } ii_keyword_entry_dynarr; +extern const struct struct_description iim_description; + struct image_instantiator_methods { Lisp_Object symbol; @@ -176,12 +181,14 @@ Dynarr_new (console_type_entry); \ add_entry_to_image_instantiator_format_list \ (Q##format, format##_image_instantiator_methods); \ + dumpstruct (&format##_image_instantiator_methods, \ + &iim_description); \ } while (0) #define INITIALIZE_IMAGE_INSTANTIATOR_FORMAT(format, obj_name) \ do { \ defsymbol (&Q##format, obj_name); \ - INITIALIZE_IMAGE_INSTANTIATOR_FORMAT_NO_SYM(format, obj_name); \ + INITIALIZE_IMAGE_INSTANTIATOR_FORMAT_NO_SYM(format, obj_name);\ } while (0) /* Declare that image-instantiator format FORMAT has method M; used in @@ -235,23 +242,27 @@ DECLARE_IMAGE_INSTANTIATOR_FORMAT(format); \ struct image_instantiator_methods *type##_##format##_image_instantiator_methods -#define INITIALIZE_DEVICE_IIFORMAT(type, format) \ -do { \ - type##_##format##_image_instantiator_methods = \ - xnew_and_zero (struct image_instantiator_methods); \ +#define INITIALIZE_DEVICE_IIFORMAT(type, format) \ +do { \ + type##_##format##_image_instantiator_methods = \ + xnew_and_zero (struct image_instantiator_methods); \ type##_##format##_image_instantiator_methods->symbol = Q##format; \ type##_##format##_image_instantiator_methods->device = Q##type; \ type##_##format##_image_instantiator_methods->keywords = \ - Dynarr_new (ii_keyword_entry); \ - add_entry_to_device_ii_format_list \ + Dynarr_new (ii_keyword_entry); \ + add_entry_to_device_ii_format_list \ (Q##type, Q##format, type##_##format##_image_instantiator_methods); \ - IIFORMAT_VALID_CONSOLE(type,format); \ + IIFORMAT_VALID_CONSOLE(type,format); \ + dumpstruct (&type##_##format##_image_instantiator_methods, \ + &iim_description); \ } while (0) /* Declare that image-instantiator format FORMAT has method M; used in initialization routines */ #define IIFORMAT_HAS_DEVMETHOD(type, format, m) \ (type##_##format##_image_instantiator_methods->m##_method = type##_##format##_##m) +#define IIFORMAT_HAS_SHARED_DEVMETHOD(type, format, m, fromformat) \ + (type##_##format##_image_instantiator_methods->m##_method = type##_##fromformat##_##m) struct image_instantiator_methods * decode_device_ii_format (Lisp_Object device, Lisp_Object format, @@ -279,11 +290,16 @@ void check_valid_int (Lisp_Object data); void check_valid_face (Lisp_Object data); void check_valid_vector (Lisp_Object data); +void check_valid_item_list_1 (Lisp_Object items); void initialize_subwindow_image_instance (struct Lisp_Image_Instance*); void subwindow_instantiate (Lisp_Object image_instance, Lisp_Object instantiator, Lisp_Object pointer_fg, Lisp_Object pointer_bg, int dest_mask, Lisp_Object domain); +void widget_instantiate_1 (Lisp_Object image_instance, Lisp_Object instantiator, + Lisp_Object pointer_fg, Lisp_Object pointer_bg, + int dest_mask, Lisp_Object domain, int default_textheight, + int default_pixheight, int default_textwidth); DECLARE_DOESNT_RETURN (incompatible_image_types (Lisp_Object instantiator, int given_dest_mask, @@ -330,7 +346,6 @@ XRECORD (x, image_instance, struct Lisp_Image_Instance) #define XSETIMAGE_INSTANCE(x, p) XSETRECORD (x, p, image_instance) #define IMAGE_INSTANCEP(x) RECORDP (x, image_instance) -#define GC_IMAGE_INSTANCEP(x) GC_RECORDP (x, image_instance) #define CHECK_IMAGE_INSTANCE(x) CHECK_RECORD (x, image_instance) #define CONCHECK_IMAGE_INSTANCE(x) CONCHECK_RECORD (x, image_instance) @@ -343,7 +358,8 @@ IMAGE_COLOR_PIXMAP, IMAGE_POINTER, IMAGE_SUBWINDOW, - IMAGE_WIDGET + IMAGE_WIDGET, + IMAGE_LAYOUT }; #define IMAGE_NOTHING_MASK (1 << 0) @@ -353,6 +369,7 @@ #define IMAGE_POINTER_MASK (1 << 4) #define IMAGE_SUBWINDOW_MASK (1 << 5) #define IMAGE_WIDGET_MASK (1 << 6) +#define IMAGE_LAYOUT_MASK (1 << 7) #define IMAGE_INSTANCE_TYPE_P(ii, type) \ (IMAGE_INSTANCEP (ii) && XIMAGE_INSTANCE_TYPE (ii) == type) @@ -371,15 +388,17 @@ IMAGE_INSTANCE_TYPE_P (ii, IMAGE_SUBWINDOW) #define WIDGET_IMAGE_INSTANCEP(ii) \ IMAGE_INSTANCE_TYPE_P (ii, IMAGE_WIDGET) +#define LAYOUT_IMAGE_INSTANCEP(ii) \ + IMAGE_INSTANCE_TYPE_P (ii, IMAGE_LAYOUT) -#define CHECK_NOTHING_IMAGE_INSTANCE(x) do { \ - CHECK_IMAGE_INSTANCE (x); \ +#define CHECK_NOTHING_IMAGE_INSTANCE(x) do { \ + CHECK_IMAGE_INSTANCE (x); \ if (!NOTHING_IMAGE_INSTANCEP (x)) \ x = wrong_type_argument (Qnothing_image_instance_p, (x)); \ } while (0) -#define CHECK_TEXT_IMAGE_INSTANCE(x) do { \ - CHECK_IMAGE_INSTANCE (x); \ +#define CHECK_TEXT_IMAGE_INSTANCE(x) do { \ + CHECK_IMAGE_INSTANCE (x); \ if (!TEXT_IMAGE_INSTANCEP (x)) \ x = wrong_type_argument (Qtext_image_instance_p, (x)); \ } while (0) @@ -390,37 +409,45 @@ x = wrong_type_argument (Qmono_pixmap_image_instance_p, (x)); \ } while (0) -#define CHECK_COLOR_PIXMAP_IMAGE_INSTANCE(x) do { \ - CHECK_IMAGE_INSTANCE (x); \ +#define CHECK_COLOR_PIXMAP_IMAGE_INSTANCE(x) do { \ + CHECK_IMAGE_INSTANCE (x); \ if (!COLOR_PIXMAP_IMAGE_INSTANCEP (x)) \ x = wrong_type_argument (Qcolor_pixmap_image_instance_p, (x)); \ } while (0) -#define CHECK_POINTER_IMAGE_INSTANCE(x) do { \ - CHECK_IMAGE_INSTANCE (x); \ +#define CHECK_POINTER_IMAGE_INSTANCE(x) do { \ + CHECK_IMAGE_INSTANCE (x); \ if (!POINTER_IMAGE_INSTANCEP (x)) \ x = wrong_type_argument (Qpointer_image_instance_p, (x)); \ } while (0) -#define CHECK_SUBWINDOW_IMAGE_INSTANCE(x) do { \ +#define CHECK_SUBWINDOW_IMAGE_INSTANCE(x) do { \ CHECK_IMAGE_INSTANCE (x); \ if (!SUBWINDOW_IMAGE_INSTANCEP (x) \ && !WIDGET_IMAGE_INSTANCEP (x)) \ x = wrong_type_argument (Qsubwindow_image_instance_p, (x)); \ } while (0) -#define CHECK_WIDGET_IMAGE_INSTANCE(x) do { \ - CHECK_IMAGE_INSTANCE (x); \ +#define CHECK_WIDGET_IMAGE_INSTANCE(x) do { \ + CHECK_IMAGE_INSTANCE (x); \ if (!WIDGET_IMAGE_INSTANCEP (x)) \ x = wrong_type_argument (Qwidget_image_instance_p, (x)); \ } while (0) +#define CHECK_LAYOUT_IMAGE_INSTANCE(x) do { \ + CHECK_IMAGE_INSTANCE (x); \ + if (!LAYOUT_IMAGE_INSTANCEP (x)) \ + x = wrong_type_argument (Qlayout_image_instance_p, (x)); \ +} while (0) + struct Lisp_Image_Instance { struct lcrecord_header header; Lisp_Object device; Lisp_Object name; enum image_instance_type type; + int x_offset, y_offset; /* for layout purposes */ + unsigned int dirty : 1; union { struct @@ -430,6 +457,7 @@ struct { int width, height, depth; + int slice, maxslice, timeout; Lisp_Object hotspot_x, hotspot_y; /* integer or Qnil */ Lisp_Object filename; /* string or Qnil */ Lisp_Object mask_filename; /* string or Qnil */ @@ -438,20 +466,29 @@ or a pointer */ Lisp_Object auxdata; /* list or Qnil: any additional data to be seen from lisp */ + void* mask; /* mask that can be seen from all windowing systems */ } pixmap; /* used for pointers as well */ struct { Lisp_Object frame; unsigned int width, height; void* subwindow; /* specific devices can use this as necessary */ - int being_displayed; /* used to detect when needs to be unmapped */ - struct + unsigned int being_displayed : 1; /* used to detect when needs to be unmapped */ + union { - Lisp_Object face; /* foreground and background colors */ - Lisp_Object type; - Lisp_Object props; /* properties */ - Lisp_Object gui_item; /* a list of gui_items */ - } widget; /* widgets are subwindows */ + struct + { + Lisp_Object face; /* foreground and background colors */ + Lisp_Object type; + Lisp_Object props; /* properties */ + Lisp_Object gui_item; /* a list of gui_items */ + } widget; /* widgets are subwindows */ + struct + { + Lisp_Object children; /* managed children */ + Lisp_Object border; /* Style of enclosing border or text. */ + } layout; + } s; } subwindow; } u; @@ -462,9 +499,12 @@ #define IMAGE_INSTANCE_DEVICE(i) ((i)->device) #define IMAGE_INSTANCE_NAME(i) ((i)->name) #define IMAGE_INSTANCE_TYPE(i) ((i)->type) +#define IMAGE_INSTANCE_XOFFSET(i) ((i)->x_offset) +#define IMAGE_INSTANCE_YOFFSET(i) ((i)->y_offset) #define IMAGE_INSTANCE_PIXMAP_TYPE_P(i) \ ((IMAGE_INSTANCE_TYPE (i) == IMAGE_MONO_PIXMAP) \ || (IMAGE_INSTANCE_TYPE (i) == IMAGE_COLOR_PIXMAP)) +#define IMAGE_INSTANCE_DIRTYP(i) ((i)->dirty) #define IMAGE_INSTANCE_TEXT_STRING(i) ((i)->u.text.string) @@ -478,6 +518,10 @@ #define IMAGE_INSTANCE_PIXMAP_FG(i) ((i)->u.pixmap.fg) #define IMAGE_INSTANCE_PIXMAP_BG(i) ((i)->u.pixmap.bg) #define IMAGE_INSTANCE_PIXMAP_AUXDATA(i) ((i)->u.pixmap.auxdata) +#define IMAGE_INSTANCE_PIXMAP_MASK(i) ((i)->u.pixmap.mask) +#define IMAGE_INSTANCE_PIXMAP_SLICE(i) ((i)->u.pixmap.slice) +#define IMAGE_INSTANCE_PIXMAP_MAXSLICE(i) ((i)->u.pixmap.maxslice) +#define IMAGE_INSTANCE_PIXMAP_TIMEOUT(i) ((i)->u.pixmap.timeout) #define IMAGE_INSTANCE_SUBWINDOW_WIDTH(i) ((i)->u.subwindow.width) #define IMAGE_INSTANCE_SUBWINDOW_HEIGHT(i) ((i)->u.subwindow.height) @@ -490,22 +534,31 @@ IMAGE_INSTANCE_SUBWINDOW_WIDTH(i) #define IMAGE_INSTANCE_WIDGET_HEIGHT(i) \ IMAGE_INSTANCE_SUBWINDOW_HEIGHT(i) -#define IMAGE_INSTANCE_WIDGET_TYPE(i) ((i)->u.subwindow.widget.type) -#define IMAGE_INSTANCE_WIDGET_PROPS(i) ((i)->u.subwindow.widget.props) -#define IMAGE_INSTANCE_WIDGET_FACE(i) ((i)->u.subwindow.widget.face) -#define IMAGE_INSTANCE_WIDGET_ITEM(i) ((i)->u.subwindow.widget.gui_item) -#define IMAGE_INSTANCE_WIDGET_SINGLE_ITEM(i) \ -(CONSP (IMAGE_INSTANCE_WIDGET_ITEM (i)) ? \ -XCAR (IMAGE_INSTANCE_WIDGET_ITEM (i)) : \ - IMAGE_INSTANCE_WIDGET_ITEM (i)) +#define IMAGE_INSTANCE_WIDGET_TYPE(i) ((i)->u.subwindow.s.widget.type) +#define IMAGE_INSTANCE_WIDGET_PROPS(i) ((i)->u.subwindow.s.widget.props) +#define IMAGE_INSTANCE_WIDGET_FACE(i) ((i)->u.subwindow.s.widget.face) +#define IMAGE_INSTANCE_WIDGET_ITEMS(i) ((i)->u.subwindow.s.widget.gui_item) +#define IMAGE_INSTANCE_WIDGET_ITEM(i) \ +(CONSP (IMAGE_INSTANCE_WIDGET_ITEMS (i)) ? \ +XCAR (IMAGE_INSTANCE_WIDGET_ITEMS (i)) : \ + IMAGE_INSTANCE_WIDGET_ITEMS (i)) #define IMAGE_INSTANCE_WIDGET_TEXT(i) XGUI_ITEM (IMAGE_INSTANCE_WIDGET_ITEM (i))->name +#define IMAGE_INSTANCE_LAYOUT_CHILDREN(i) ((i)->u.subwindow.s.layout.children) +#define IMAGE_INSTANCE_LAYOUT_BORDER(i) ((i)->u.subwindow.s.layout.border) + #define XIMAGE_INSTANCE_DEVICE(i) \ IMAGE_INSTANCE_DEVICE (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_NAME(i) \ IMAGE_INSTANCE_NAME (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_TYPE(i) \ IMAGE_INSTANCE_TYPE (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_XOFFSET(i) \ + IMAGE_INSTANCE_XOFFSET (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_YOFFSET(i) \ + IMAGE_INSTANCE_YOFFSET (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_DIRTYP(i) \ + IMAGE_INSTANCE_DIRTYP (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_TEXT_STRING(i) \ IMAGE_INSTANCE_TEXT_STRING (XIMAGE_INSTANCE (i)) @@ -528,6 +581,14 @@ IMAGE_INSTANCE_PIXMAP_FG (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_PIXMAP_BG(i) \ IMAGE_INSTANCE_PIXMAP_BG (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_PIXMAP_MASK(i) \ + IMAGE_INSTANCE_PIXMAP_MASK (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_PIXMAP_SLICE(i) \ + IMAGE_INSTANCE_PIXMAP_SLICE (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_PIXMAP_MAXSLICE(i) \ + IMAGE_INSTANCE_PIXMAP_MAXSLICE (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_PIXMAP_TIMEOUT(i) \ + IMAGE_INSTANCE_PIXMAP_TIMEOUT (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_WIDGET_WIDTH(i) \ IMAGE_INSTANCE_WIDGET_WIDTH (XIMAGE_INSTANCE (i)) @@ -541,11 +602,16 @@ IMAGE_INSTANCE_WIDGET_FACE (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_WIDGET_ITEM(i) \ IMAGE_INSTANCE_WIDGET_ITEM (XIMAGE_INSTANCE (i)) -#define XIMAGE_INSTANCE_WIDGET_SINGLE_ITEM(i) \ - IMAGE_INSTANCE_WIDGET_SINGLE_ITEM (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_WIDGET_ITEMS(i) \ + IMAGE_INSTANCE_WIDGET_ITEMS (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_WIDGET_TEXT(i) \ IMAGE_INSTANCE_WIDGET_TEXT (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_LAYOUT_CHILDREN(i) \ + IMAGE_INSTANCE_LAYOUT_CHILDREN (XIMAGE_INSTANCE (i)) +#define XIMAGE_INSTANCE_LAYOUT_BORDER(i) \ + IMAGE_INSTANCE_LAYOUT_BORDER (XIMAGE_INSTANCE (i)) + #define XIMAGE_INSTANCE_SUBWINDOW_WIDTH(i) \ IMAGE_INSTANCE_SUBWINDOW_WIDTH (XIMAGE_INSTANCE (i)) #define XIMAGE_INSTANCE_SUBWINDOW_HEIGHT(i) \ @@ -557,6 +623,9 @@ #define XIMAGE_INSTANCE_SUBWINDOW_DISPLAYEDP(i) \ IMAGE_INSTANCE_SUBWINDOW_DISPLAYEDP (XIMAGE_INSTANCE (i)) +#define MARK_IMAGE_INSTANCE_CHANGED(i) \ + (IMAGE_INSTANCE_DIRTYP (i) = 1); + #ifdef HAVE_XPM Lisp_Object evaluate_xpm_color_symbols (void); Lisp_Object pixmap_to_lisp_data (Lisp_Object name, int ok_if_data_invalid); @@ -596,17 +665,19 @@ Lisp_Object baseline; /* percent above baseline */ Lisp_Object face; /* if non-nil, face to use when displaying */ - + Lisp_Object plist; void (*after_change) (Lisp_Object glyph, Lisp_Object property, Lisp_Object locale); + + unsigned int dirty : 1; /* So that we can selectively + redisplay changed glyphs. */ }; DECLARE_LRECORD (glyph, struct Lisp_Glyph); #define XGLYPH(x) XRECORD (x, glyph, struct Lisp_Glyph) #define XSETGLYPH(x, p) XSETRECORD (x, p, glyph) #define GLYPHP(x) RECORDP (x, glyph) -#define GC_GLYPHP(x) GC_RECORDP (x, glyph) #define CHECK_GLYPH(x) CHECK_RECORD (x, glyph) #define CONCHECK_GLYPH(x) CONCHECK_RECORD (x, glyph) @@ -633,21 +704,26 @@ #define GLYPH_CONTRIB_P(g) ((g)->contrib_p) #define GLYPH_BASELINE(g) ((g)->baseline) #define GLYPH_FACE(g) ((g)->face) +#define GLYPH_DIRTYP(g) ((g)->dirty) #define XGLYPH_TYPE(g) GLYPH_TYPE (XGLYPH (g)) #define XGLYPH_IMAGE(g) GLYPH_IMAGE (XGLYPH (g)) #define XGLYPH_CONTRIB_P(g) GLYPH_CONTRIB_P (XGLYPH (g)) #define XGLYPH_BASELINE(g) GLYPH_BASELINE (XGLYPH (g)) #define XGLYPH_FACE(g) GLYPH_FACE (XGLYPH (g)) +#define XGLYPH_DIRTYP(g) GLYPH_DIRTYP (XGLYPH (g)) -extern Lisp_Object Qxpm, Qxface; +#define MARK_GLYPH_CHANGED(g) (GLYPH_DIRTYP (g) = 1); + +extern Lisp_Object Qxpm, Qxface, Qetched_in, Qetched_out, Qbevel_in, Qbevel_out; extern Lisp_Object Q_data, Q_file, Q_color_symbols, Qconst_glyph_variable; extern Lisp_Object Qxbm, Qedit_field, Qgroup, Qlabel, Qcombo_box, Qscrollbar; -extern Lisp_Object Qtree_view, Qtab_control, Qprogress_gauge; +extern Lisp_Object Qtree_view, Qtab_control, Qprogress_gauge, Q_border; extern Lisp_Object Q_mask_file, Q_mask_data, Q_hotspot_x, Q_hotspot_y; extern Lisp_Object Q_foreground, Q_background, Q_face, Q_descriptor, Q_group; extern Lisp_Object Q_width, Q_height, Q_pixel_width, Q_pixel_height, Q_text; extern Lisp_Object Q_items, Q_properties, Q_image, Q_percent, Qimage_conversion_error; +extern Lisp_Object Q_orientation; extern Lisp_Object Vcontinuation_glyph, Vcontrol_arrow_glyph, Vhscroll_glyph; extern Lisp_Object Vinvisible_text_glyph, Voctal_escape_glyph, Vtruncation_glyph; extern Lisp_Object Vxemacs_logo; @@ -688,6 +764,8 @@ void widget_text_to_pixel_conversion (Lisp_Object domain, Lisp_Object face, int th, int tw, int* height, int* width); +Lisp_Object add_glyph_animated_timeout (EMACS_INT tickms, Lisp_Object device); +void disable_glyph_animated_timeout (int i); /************************************************************************/ /* Glyph Cachels */ @@ -698,7 +776,14 @@ { Lisp_Object glyph; + unsigned int dirty :1; /* I'm copying faces here. I'm not + sure why we need two dirty + flags. Maybe because an image + instance can be dirty and so we + need to frob this in the same way + as other image instance properties. */ unsigned int updated :1; + unsigned short width; unsigned short ascent; unsigned short descent; @@ -721,11 +806,14 @@ Dynarr_atp (window->glyph_cachels, index)->ascent #define GLYPH_CACHEL_DESCENT(window, index) \ Dynarr_atp (window->glyph_cachels, index)->descent +#define GLYPH_CACHEL_DIRTYP(window, index) \ + Dynarr_atp (window->glyph_cachels, index)->dirty -void mark_glyph_cachels (glyph_cachel_dynarr *elements, - void (*markobj) (Lisp_Object)); +void mark_glyph_cachels (glyph_cachel_dynarr *elements); void mark_glyph_cachels_as_not_updated (struct window *w); +void mark_glyph_cachels_as_clean (struct window *w); void reset_glyph_cachels (struct window *w); +glyph_index get_glyph_cachel_index (struct window *w, Lisp_Object glyph); #ifdef MEMORY_USAGE_STATS int compute_glyph_cachel_usage (glyph_cachel_dynarr *glyph_cachels, @@ -752,8 +840,8 @@ Lisp_Object subwindow; int x, y; int width, height; - int being_displayed; - int updated; + unsigned int being_displayed : 1; + unsigned int updated : 1; }; typedef struct @@ -761,12 +849,25 @@ Dynarr_declare (subwindow_cachel); } subwindow_cachel_dynarr; -void mark_subwindow_cachels (subwindow_cachel_dynarr *elements, - void (*markobj) (Lisp_Object)); +void mark_subwindow_cachels (subwindow_cachel_dynarr *elements); void mark_subwindow_cachels_as_not_updated (struct frame *f); void reset_subwindow_cachels (struct frame *f); void unmap_subwindow (Lisp_Object subwindow); -void map_subwindow (Lisp_Object subwindow, int x, int y); +void map_subwindow (Lisp_Object subwindow, int x, int y, + struct display_glyph_area *dga); void update_frame_subwindows (struct frame *f); +int find_matching_subwindow (struct frame* f, int x, int y, int width, int height); + +struct expose_ignore +{ + int x; + int y; + int width; + int height; + struct expose_ignore *next; +}; + +int check_for_ignored_expose (struct frame* f, int x, int y, int width, int height); +extern int hold_ignored_expose_registration; #endif /* _XEMACS_GLYPHS_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/gui-msw.c --- a/src/gui-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gui-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -46,7 +46,7 @@ if (NILP (data) || UNBOUNDP (data)) return Qnil; - MARK_SUBWINDOWS_CHANGED; + MARK_SUBWINDOWS_STATE_CHANGED; /* Ok, this is our one. Enqueue it. */ get_gui_callback (data, &fn, &arg); XSETFRAME (frame, f); diff -r 28d9c139be4c -r 11054d720c21 src/gui-x.c --- a/src/gui-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gui-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -58,34 +58,26 @@ } -struct mark_widget_value_closure -{ - void (*markobj) (Lisp_Object); -}; - static int mark_widget_value_mapper (widget_value *val, void *closure) { Lisp_Object markee; - - struct mark_widget_value_closure *cl = - (struct mark_widget_value_closure *) closure; if (val->call_data) { VOID_TO_LISP (markee, val->call_data); - (cl->markobj) (markee); + mark_object (markee); } if (val->accel) { VOID_TO_LISP (markee, val->accel); - (cl->markobj) (markee); + mark_object (markee); } return 0; } static Lisp_Object -mark_popup_data (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_popup_data (Lisp_Object obj) { struct popup_data *data = (struct popup_data *) XPOPUP_DATA (obj); @@ -93,12 +85,7 @@ call-data */ if (data->id) - { - struct mark_widget_value_closure closure; - - closure.markobj = markobj; - lw_map_widget_values (data->id, mark_widget_value_mapper, &closure); - } + lw_map_widget_values (data->id, mark_widget_value_mapper, 0); return data->last_menubar_buffer; } @@ -257,7 +244,7 @@ } else { - MARK_SUBWINDOWS_CHANGED; + MARK_SUBWINDOWS_STATE_CHANGED; get_gui_callback (data, &fn, &arg); } @@ -325,7 +312,20 @@ /* !!#### This function has not been Mule-ized */ /* This function cannot GC because gc_currently_forbidden is set when it's called */ - struct Lisp_Gui_Item* pgui = XGUI_ITEM (gui_item); + struct Lisp_Gui_Item* pgui = 0; + + /* degenerate case */ + if (STRINGP (gui_item)) + { + wv->type = TEXT_TYPE; + wv->name = (char *) XSTRING_DATA (gui_item); + wv->name = xstrdup (wv->name); + return 1; + } + else if (!GUI_ITEMP (gui_item)) + signal_simple_error("need a string or a gui_item here", gui_item); + + pgui = XGUI_ITEM (gui_item); if (!NILP (pgui->filter)) signal_simple_error(":filter keyword not permitted on leaf nodes", gui_item); @@ -340,6 +340,7 @@ CHECK_STRING (pgui->name); wv->name = (char *) XSTRING_DATA (pgui->name); + wv->name = xstrdup (wv->name); wv->accel = LISP_TO_VOID (gui_item_accelerator (gui_item)); if (!NILP (pgui->suffix)) @@ -448,6 +449,111 @@ return 1; } +/* parse tree's of gui items into widget_value hierarchies */ +static void gui_item_children_to_widget_values (Lisp_Object items, widget_value* parent); + +static widget_value * +gui_items_to_widget_values_1 (Lisp_Object items, widget_value* parent, + widget_value* prev) +{ + widget_value* wv = 0; + + assert ((parent || prev) && !(parent && prev)); + /* now walk the tree creating widget_values as appropriate */ + if (!CONSP (items)) + { + wv = xmalloc_widget_value(); + if (parent) + parent->contents = wv; + else + prev->next = wv; + if (!button_item_to_widget_value (items, wv, 0, 1)) + { + free_widget_value (wv); + if (parent) + parent->contents = 0; + else + prev->next = 0; + } + else + { + wv->value = xstrdup (wv->name); /* what a mess... */ + } + } + else + { + /* first one is the parent */ + if (CONSP (XCAR (items))) + signal_simple_error ("parent item must not be a list", XCAR (items)); + + if (parent) + wv = gui_items_to_widget_values_1 (XCAR (items), parent, 0); + else + wv = gui_items_to_widget_values_1 (XCAR (items), 0, prev); + /* the rest are the children */ + gui_item_children_to_widget_values (XCDR (items), wv); + } + return wv; +} + +static void +gui_item_children_to_widget_values (Lisp_Object items, widget_value* parent) +{ + widget_value* wv = 0, *prev = 0; + Lisp_Object rest; + CHECK_CONS (items); + + /* first one is master */ + prev = gui_items_to_widget_values_1 (XCAR (items), parent, 0); + /* the rest are the children */ + LIST_LOOP (rest, XCDR (items)) + { + Lisp_Object tab = XCAR (rest); + wv = gui_items_to_widget_values_1 (tab, 0, prev); + prev = wv; + } +} + +widget_value * +gui_items_to_widget_values (Lisp_Object items) +{ + /* !!#### This function has not been Mule-ized */ + /* This function can GC */ + widget_value *control = 0, *tmp = 0; + int count = specpdl_depth (); + Lisp_Object wv_closure; + + if (NILP (items)) + signal_simple_error ("must have some items", items); + + /* Inhibit GC during this conversion. The reasons for this are + the same as in menu_item_descriptor_to_widget_value(); see + the large comment above that function. */ + record_unwind_protect (restore_gc_inhibit, + make_int (gc_currently_forbidden)); + gc_currently_forbidden = 1; + + /* Also make sure that we free the partially-created widget_value + tree on Lisp error. */ + control = xmalloc_widget_value(); + wv_closure = make_opaque_ptr (control); + record_unwind_protect (widget_value_unwind, wv_closure); + + gui_items_to_widget_values_1 (items, control, 0); + + /* mess about getting the data we really want */ + tmp = control; + control = control->contents; + tmp->next = 0; + tmp->contents = 0; + free_widget_value (tmp); + + /* No more need to free the half-filled-in structures. */ + set_opaque_ptr (wv_closure, 0); + unbind_to (count, Qnil); + + return control; +} /* This is a kludge to make sure emacs can only link against a version of lwlib that was compiled in the right way. Emacs references symbols which @@ -498,6 +604,11 @@ #elif defined (HAVE_DIALOGS) MACROLET (lwlib_dialogs_athena); #endif +#ifdef LWLIB_WIDGETS_MOTIF + MACROLET (lwlib_widgets_motif); +#elif defined (HAVE_WIDGETS) + MACROLET (lwlib_widgets_athena); +#endif #undef MACROLET } @@ -509,11 +620,21 @@ } void -vars_of_gui_x (void) +reinit_vars_of_gui_x (void) { lwlib_id_tick = (1<<16); /* start big, to not conflict with Energize */ +#ifdef HAVE_POPUPS + popup_up_p = 0; +#endif - popup_up_p = 0; + /* this makes only safe calls as in emacs.c */ + sanity_check_lwlib (); +} + +void +vars_of_gui_x (void) +{ + reinit_vars_of_gui_x (); Vpopup_callbacks = Qnil; staticpro (&Vpopup_callbacks); @@ -527,7 +648,4 @@ */ ); #endif Fset (Qmenu_no_selection_hook, Qnil); - - /* this makes only safe calls as in emacs.c */ - sanity_check_lwlib (); } diff -r 28d9c139be4c -r 11054d720c21 src/gui-x.h --- a/src/gui-x.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gui-x.h Mon Aug 13 11:26:11 2007 +0200 @@ -30,8 +30,6 @@ LWLIB_ID new_lwlib_id (void); -#ifdef HAVE_POPUPS - /* Each frame has one of these, and they are also contained in Vpopup_callbacks. It doesn't really need to be an lrecord (it's not lisp-accessible) @@ -62,7 +60,6 @@ #define XPOPUP_DATA(x) XRECORD (x, popup_data, struct popup_data) #define XSETPOPUP_DATA(x, p) XSETRECORD (x, p, popup_data) #define POPUP_DATAP(x) RECORDP (x, popup_data) -#define GC_POPUP_DATAP(x) GC_RECORDP (x, popup_data) #define CHECK_POPUP_DATA(x) CHECK_RECORD (x, popup_data) void gcpro_popup_callbacks (LWLIB_ID id); @@ -73,10 +70,9 @@ XtPointer client_data); int button_item_to_widget_value (Lisp_Object desc, widget_value *wv, int allow_text_field_p, int no_keys_p); +widget_value * gui_items_to_widget_values (Lisp_Object items); Lisp_Object menu_name_to_accelerator (char *name); char *menu_separator_style (CONST char *s); Lisp_Object widget_value_unwind (Lisp_Object closure); -#endif /* HAVE_POPUPS */ - #endif /* _XEMACS_XLWLIB_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/gui.c --- a/src/gui.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gui.c Mon Aug 13 11:26:11 2007 +0200 @@ -34,6 +34,8 @@ Lisp_Object Q_accelerator, Q_label, Q_callback; Lisp_Object Qtoggle, Qradio; +static Lisp_Object parse_gui_item_tree_list (Lisp_Object list); + #ifdef HAVE_POPUPS /* count of menus/dboxes currently up */ @@ -152,7 +154,7 @@ } Lisp_Object -allocate_gui_item () +allocate_gui_item (void) { struct Lisp_Gui_Item *lp = alloc_lcrecord_type (struct Lisp_Gui_Item, &lrecord_gui_item); @@ -381,6 +383,7 @@ gui_item_display_flush_left (Lisp_Object gui_item, char* buf, Bytecount buf_len) { + /* This function can call lisp */ char *p = buf; Bytecount len; struct Lisp_Gui_Item* pgui_item = XGUI_ITEM (gui_item); @@ -468,22 +471,22 @@ #endif /* HAVE_WINDOW_SYSTEM */ static Lisp_Object -mark_gui_item (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_gui_item (Lisp_Object obj) { struct Lisp_Gui_Item *p = XGUI_ITEM (obj); - markobj (p->name); - markobj (p->callback); - markobj (p->config); - markobj (p->suffix); - markobj (p->active); - markobj (p->included); - markobj (p->config); - markobj (p->filter); - markobj (p->style); - markobj (p->selected); - markobj (p->keys); - markobj (p->accelerator); + mark_object (p->name); + mark_object (p->callback); + mark_object (p->config); + mark_object (p->suffix); + mark_object (p->active); + mark_object (p->included); + mark_object (p->config); + mark_object (p->filter); + mark_object (p->style); + mark_object (p->selected); + mark_object (p->keys); + mark_object (p->accelerator); return Qnil; } @@ -563,6 +566,56 @@ write_c_string (buf, printcharfun); } +/* parse a glyph descriptor into a tree of gui items. + + The gui_item slot of an image instance can be a single item or an + arbitrarily nested hierarchy of item lists. */ + +static Lisp_Object parse_gui_item_tree_item (Lisp_Object entry) +{ + Lisp_Object ret = entry; + if (VECTORP (entry)) + { + ret = gui_parse_item_keywords_no_errors (entry); + } + else if (STRINGP (entry)) + { + CHECK_STRING (entry); + } + else + signal_simple_error ("item must be a vector or a string", entry); + + return ret; +} + +Lisp_Object parse_gui_item_tree_children (Lisp_Object list) +{ + Lisp_Object rest, ret = Qnil; + CHECK_CONS (list); + /* recursively add items to the tree view */ + LIST_LOOP (rest, list) + { + Lisp_Object sub; + if (CONSP (XCAR (rest))) + sub = parse_gui_item_tree_list (XCAR (rest)); + else + sub = parse_gui_item_tree_item (XCAR (rest)); + + ret = Fcons (sub, ret); + } + /* make the order the same as the items we have parsed */ + return Fnreverse (ret); +} + +static Lisp_Object parse_gui_item_tree_list (Lisp_Object list) +{ + Lisp_Object ret; + CHECK_CONS (list); + /* first one can never be a list */ + ret = parse_gui_item_tree_item (XCAR (list)); + return Fcons (ret, parse_gui_item_tree_children (XCDR (list))); +} + DEFINE_LRECORD_IMPLEMENTATION ("gui-item", gui_item, mark_gui_item, print_gui_item, 0, gui_item_equal, diff -r 28d9c139be4c -r 11054d720c21 src/gui.h --- a/src/gui.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gui.h Mon Aug 13 11:26:11 2007 +0200 @@ -41,7 +41,6 @@ XRECORD (x, gui_item, struct Lisp_Gui_Item) #define XSETGUI_ITEM(x, p) XSETRECORD (x, p, gui_item) #define GUI_ITEMP(x) RECORDP (x, gui_item) -#define GC_GUI_ITEMP(x) GC_RECORDP (x, gui_item) #define CHECK_GUI_ITEM(x) CHECK_RECORD (x, gui_item) #define CONCHECK_GUI_ITEM(x) CONCHECK_RECORD (x, gui_item) @@ -83,8 +82,9 @@ unsigned int gui_item_display_flush_right (Lisp_Object gui_item, char* buf, Bytecount buf_len); -Lisp_Object allocate_gui_item (); +Lisp_Object allocate_gui_item (void); void gui_item_init (Lisp_Object gui_item); +Lisp_Object parse_gui_item_tree_children (Lisp_Object list); /* this is mswindows biased but reasonably safe I think */ #define GUI_ITEM_ID_SLOTS 8 diff -r 28d9c139be4c -r 11054d720c21 src/gutter.c --- a/src/gutter.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gutter.c Mon Aug 13 11:26:11 2007 +0200 @@ -20,7 +20,8 @@ /* Synched up with: Not in FSF. */ -/* Specifers ripped-off from toolbar.c */ +/* written by Andy Piper with specifiers partially + ripped-off from toolbar.c */ #include #include "lisp.h" @@ -45,25 +46,27 @@ Lisp_Object Vdefault_gutter_position; -#define SET_GUTTER_WAS_VISIBLE_FLAG(frame, pos, flag) \ - do { \ - switch (pos) \ - { \ - case TOP_GUTTER: \ - (frame)->top_gutter_was_visible = flag; \ - break; \ - case BOTTOM_GUTTER: \ - (frame)->bottom_gutter_was_visible = flag; \ - break; \ - case LEFT_GUTTER: \ - (frame)->left_gutter_was_visible = flag; \ - break; \ - case RIGHT_GUTTER: \ - (frame)->right_gutter_was_visible = flag; \ - break; \ - default: \ - abort (); \ - } \ +Lisp_Object Qgutter_size; + +#define SET_GUTTER_WAS_VISIBLE_FLAG(frame, pos, flag) \ + do { \ + switch (pos) \ + { \ + case TOP_GUTTER: \ + (frame)->top_gutter_was_visible = flag; \ + break; \ + case BOTTOM_GUTTER: \ + (frame)->bottom_gutter_was_visible = flag; \ + break; \ + case LEFT_GUTTER: \ + (frame)->left_gutter_was_visible = flag; \ + break; \ + case RIGHT_GUTTER: \ + (frame)->right_gutter_was_visible = flag; \ + break; \ + default: \ + abort (); \ + } \ } while (0) static int gutter_was_visible (struct frame* frame, enum gutter_pos pos) @@ -71,13 +74,13 @@ switch (pos) { case TOP_GUTTER: - return (frame)->top_gutter_was_visible; + return frame->top_gutter_was_visible; case BOTTOM_GUTTER: - return (frame)->bottom_gutter_was_visible; + return frame->bottom_gutter_was_visible; case LEFT_GUTTER: - return (frame)->left_gutter_was_visible; + return frame->left_gutter_was_visible; case RIGHT_GUTTER: - return (frame)->right_gutter_was_visible; + return frame->right_gutter_was_visible; default: abort (); } @@ -159,7 +162,7 @@ use this for calculating the gutter positions we run into trouble if it is not the window nearest the gutter. Instead we predetermine the nearest window and then use that.*/ -void +static void get_gutter_coords (struct frame *f, enum gutter_pos pos, int *x, int *y, int *width, int *height) { @@ -224,19 +227,20 @@ face_index findex = get_builtin_face_cache_index (w, Vgui_element_face); display_line_dynarr* ddla, *cdla; struct display_line *dl; + int cdla_len; if (!f->current_display_lines) f->current_display_lines = Dynarr_new (display_line); if (!f->desired_display_lines) f->desired_display_lines = Dynarr_new (display_line); - + ddla = f->desired_display_lines; cdla = f->current_display_lines; + cdla_len = Dynarr_length (cdla); XSETFRAME (frame, f); get_gutter_coords (f, pos, &x, &y, &width, &height); - /* clear out what we want to cover */ /* generate some display lines */ generate_displayable_area (w, WINDOW_GUTTER (w, pos), x + border_width, y + border_width, @@ -248,22 +252,28 @@ output_display_line (w, cdla, ddla, line, -1, -1); } + /* If the number of display lines has shrunk, adjust. */ + if (cdla_len > Dynarr_length (ddla)) + { + Dynarr_length (cdla) = Dynarr_length (ddla); + } + /* grab coordinates of last line and blank after it. */ dl = Dynarr_atp (ddla, Dynarr_length (ddla) - 1); ypos = dl->ypos + dl->descent - dl->clip; redisplay_clear_region (window, findex, x + border_width , ypos, - width - 2 * border_width, height - (ypos - y)); - + width - 2 * border_width, height - (ypos - y) - border_width); /* bevel the gutter area if so desired */ if (border_width != 0) { MAYBE_DEVMETH (d, bevel_area, - (w, findex, x, y, width, height, border_width)); + (w, findex, x, y, width, height, border_width, + EDGE_ALL, EDGE_BEVEL_OUT)); } } /* sizing gutters is a pain so we try and help the user by detemining - what height will accomodate all lines. This is useless on left and + what height will accommodate all lines. This is useless on left and right gutters as we always have a maximal number of lines. */ static Lisp_Object calculate_gutter_size (struct window *w, enum gutter_pos pos) @@ -279,7 +289,9 @@ /* degenerate case */ if (NILP (WINDOW_GUTTER (w, pos)) || - !FRAME_VISIBLE_P (f)) + !FRAME_VISIBLE_P (f) + || + NILP (w->buffer)) return Qnil; ddla = Dynarr_new (display_line); @@ -296,12 +308,12 @@ { dl = Dynarr_atp (ddla, Dynarr_length (ddla) - 1); ypos = dl->ypos + dl->descent - dl->clip; - Dynarr_free (ddla); + free_display_lines (ddla); return make_int (ypos); } else { - Dynarr_free (ddla); + free_display_lines (ddla); return Qnil; } } @@ -323,21 +335,39 @@ void update_frame_gutters (struct frame *f) { - if (f->gutter_changed || f->frame_changed || f->clear) + if (f->gutter_changed || f->clear || + f->glyphs_changed || f->subwindows_changed || + f->windows_changed || f->windows_structure_changed || + f->extents_changed || f->faces_changed) { - int pos; + enum gutter_pos pos; + + /* We don't actually care about these when outputting the gutter + so locally disable them. */ + int local_clip_changed = f->clip_changed; + int local_buffers_changed = f->buffers_changed; + f->clip_changed = 0; + f->buffers_changed = 0; + /* and output */ - - for (pos = 0; pos < 4; pos++) + GUTTER_POS_LOOP (pos) { if (FRAME_GUTTER_VISIBLE (f, pos)) - output_gutter (f, pos); + output_gutter (f, pos); else if (gutter_was_visible (f, pos)) clear_gutter (f, pos); } - + f->clip_changed = local_clip_changed; + f->buffers_changed = local_buffers_changed; + f->gutter_changed = 0; } - f->gutter_changed = 0; +} + +void +reset_gutter_display_lines (struct frame* f) +{ + if (f->current_display_lines) + Dynarr_reset (f->current_display_lines); } static void @@ -345,11 +375,10 @@ int width, int height) { int g_x, g_y, g_width, g_height; - int newx, newy; get_gutter_coords (f, pos, &g_x, &g_y, &g_width, &g_height); - if (((y + height) < g_y) || (y > (g_y + g_height))) + if (((y + height) < g_y) || (y > (g_y + g_height)) || !height || !width || !g_height || !g_width) return; if (((x + width) < g_x) || (x > (g_x + g_width))) return; @@ -357,16 +386,7 @@ /* #### optimize this - redrawing the whole gutter for every expose is very expensive. We reset the current display lines because if they're being exposed they are no longer current. */ - if (f->current_display_lines) - Dynarr_reset (f->current_display_lines); - /* we have to do this in-case there were subwindows where we are - redrawing, unfortunately sometimes this also generates expose - events resulting in an endless cycle of redsplay. */ - newx = max (x, g_x); - newy = max (y, g_y); - width = min (x + width - newx, g_x + g_width - newx); - height = min (y + height - newy, g_y + g_height - newy); - redisplay_unmap_subwindows_maybe (f, newx, newy, width, height); + reset_gutter_display_lines (f); /* Even if none of the gutter is in the area, the blank region at the very least must be because the first thing we did is verify @@ -378,21 +398,27 @@ redraw_exposed_gutters (struct frame *f, int x, int y, int width, int height) { - int pos; - for (pos = 0; pos < 4; pos++) - { - if (FRAME_GUTTER_VISIBLE (f, pos)) - redraw_exposed_gutter (f, pos, x, y, width, height); - } + enum gutter_pos pos; + GUTTER_POS_LOOP (pos) + { + if (FRAME_GUTTER_VISIBLE (f, pos)) + redraw_exposed_gutter (f, pos, x, y, width, height); + } } void free_frame_gutters (struct frame *f) { if (f->current_display_lines) - Dynarr_free (f->current_display_lines); + { + free_display_lines (f->current_display_lines); + f->current_display_lines = 0; + } if (f->desired_display_lines) - Dynarr_free (f->desired_display_lines); + { + free_display_lines (f->desired_display_lines); + f->desired_display_lines = 0; + } } static enum gutter_pos @@ -548,8 +574,8 @@ gutter_specs_changed (Lisp_Object specifier, struct window *w, Lisp_Object oldval) { - int pos; - for (pos = 0; pos< 4; pos++) + enum gutter_pos pos; + GUTTER_POS_LOOP (pos) { w->real_gutter_size[pos] = w->gutter_size[pos]; if (EQ (w->real_gutter_size[pos], Qautodetect) @@ -573,8 +599,8 @@ gutter_geometry_changed_in_window (Lisp_Object specifier, struct window *w, Lisp_Object oldval) { - int pos; - for (pos = 0; pos< 4; pos++) + enum gutter_pos pos; + GUTTER_POS_LOOP (pos) { w->real_gutter_size[pos] = w->gutter_size[pos]; if (EQ (w->real_gutter_size[pos], Qautodetect) @@ -611,15 +637,70 @@ recompute_overlaying_specifier (Vgutter_visible_p); } + +DECLARE_SPECIFIER_TYPE (gutter_size); +#define GUTTER_SIZE_SPECIFIERP(x) SPECIFIER_TYPEP (x, gutter_size) +DEFINE_SPECIFIER_TYPE (gutter_size); + +static void +gutter_size_validate (Lisp_Object instantiator) +{ + if (NILP (instantiator)) + return; + + if (!INTP (instantiator) && !EQ (instantiator, Qautodetect)) + signal_simple_error ("Gutter size must be an integer or 'autodetect", instantiator); +} + +DEFUN ("gutter-size-specifier-p", Fgutter_size_specifier_p, 1, 1, 0, /* +Return non-nil if OBJECT is a gutter-size specifier. +*/ + (object)) +{ + return GUTTER_SIZE_SPECIFIERP (object) ? Qt : Qnil; +} + +DEFUN ("redisplay-gutter-area", Fredisplay_gutter_area, 0, 0, 0, /* +Ensure that all gutters are correctly showing their gutter specifier. +*/ + ()) +{ + Lisp_Object devcons, concons; + + DEVICE_LOOP_NO_BREAK (devcons, concons) + { + struct device *d = XDEVICE (XCAR (devcons)); + Lisp_Object frmcons; + + DEVICE_FRAME_LOOP (frmcons, d) + { + struct frame *f = XFRAME (XCAR (frmcons)); + + if (FRAME_REPAINT_P (f)) + { + update_frame_gutters (f); + } + } + + /* We now call the output_end routine for tty frames. We delay + doing so in order to avoid cursor flicker. So much for 100% + encapsulation. */ + if (DEVICE_TTY_P (d)) + DEVMETH (d, output_end, (d)); + } + + return Qnil; +} + void init_frame_gutters (struct frame *f) { - int pos; + enum gutter_pos pos; struct window* w = XWINDOW (FRAME_LAST_NONMINIBUF_WINDOW (f)); /* We are here as far in frame creation so cached specifiers are already recomputed, and possibly modified by resource initialization. We need to recalculate autodetected gutters. */ - for (pos = 0; pos< 4; pos++) + GUTTER_POS_LOOP (pos) { w->real_gutter_size[pos] = w->gutter_size[pos]; if (EQ (w->gutter_size[pos], Qautodetect) @@ -636,10 +717,14 @@ syms_of_gutter (void) { DEFSUBR (Fgutter_specifier_p); + DEFSUBR (Fgutter_size_specifier_p); DEFSUBR (Fset_default_gutter_position); DEFSUBR (Fdefault_gutter_position); DEFSUBR (Fgutter_pixel_height); DEFSUBR (Fgutter_pixel_width); + DEFSUBR (Fredisplay_gutter_area); + + defsymbol (&Qgutter_size, "gutter-size"); } void @@ -658,6 +743,17 @@ SPECIFIER_HAS_METHOD (gutter, validate); SPECIFIER_HAS_METHOD (gutter, after_change); + + INITIALIZE_SPECIFIER_TYPE (gutter_size, "gutter-size", "gutter-size-specifier-p"); + + SPECIFIER_HAS_METHOD (gutter_size, validate); +} + +void +reinit_specifier_type_create_gutter (void) +{ + REINITIALIZE_SPECIFIER_TYPE (gutter); + REINITIALIZE_SPECIFIER_TYPE (gutter_size); } void @@ -815,7 +911,7 @@ calculated to be large enough to hold the contents of the gutter. This is the default. */ ); - Vdefault_gutter_height = Fmake_specifier (Qgeneric); + Vdefault_gutter_height = Fmake_specifier (Qgutter_size); set_specifier_caching (Vdefault_gutter_height, slot_offset (struct window, default_gutter_height), @@ -842,7 +938,7 @@ See `default-gutter-height' for more information. */ ); - Vgutter_size[TOP_GUTTER] = Fmake_specifier (Qgeneric); + Vgutter_size[TOP_GUTTER] = Fmake_specifier (Qgutter_size); set_specifier_caching (Vgutter_size[TOP_GUTTER], slot_offset (struct window, gutter_size[TOP_GUTTER]), @@ -856,7 +952,7 @@ See `default-gutter-height' for more information. */ ); - Vgutter_size[BOTTOM_GUTTER] = Fmake_specifier (Qgeneric); + Vgutter_size[BOTTOM_GUTTER] = Fmake_specifier (Qgutter_size); set_specifier_caching (Vgutter_size[BOTTOM_GUTTER], slot_offset (struct window, gutter_size[BOTTOM_GUTTER]), diff -r 28d9c139be4c -r 11054d720c21 src/gutter.h --- a/src/gutter.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/gutter.h Mon Aug 13 11:26:11 2007 +0200 @@ -40,12 +40,16 @@ enum gutter_pos { - TOP_GUTTER, - BOTTOM_GUTTER, - LEFT_GUTTER, - RIGHT_GUTTER + TOP_GUTTER = 0, + BOTTOM_GUTTER = 1, + LEFT_GUTTER = 2, + RIGHT_GUTTER = 3 }; +/* Iterate over all possible gutter positions */ +#define GUTTER_POS_LOOP(var) \ +for (var = (enum gutter_pos) 0; var < 4; var = (enum gutter_pos) (var + 1)) + extern Lisp_Object Qgutter; extern Lisp_Object Vgutter_size[4]; @@ -57,6 +61,7 @@ void free_frame_gutters (struct frame *f); void redraw_exposed_gutters (struct frame *f, int x, int y, int width, int height); +void reset_gutter_display_lines (struct frame* f); #define WINDOW_GUTTER_BORDER_WIDTH(w, pos) \ (NILP ((w)->gutter_border_width[pos]) ? 0 : XINT ((w)->gutter_border_width[pos])) diff -r 28d9c139be4c -r 11054d720c21 src/input-method-xlib.c --- a/src/input-method-xlib.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/input-method-xlib.c Mon Aug 13 11:26:11 2007 +0200 @@ -140,21 +140,17 @@ static void IMDestroyCallback (XIM im, XPointer client_data, XPointer call_data) { - struct frame *f = (struct frame *)client_data; - struct device *d = XDEVICE (FRAME_DEVICE ((struct frame *)client_data)); - Lisp_Object frame_list = DEVICE_FRAME_LIST (XDEVICE (FRAME_DEVICE (f))); + struct frame *f = (struct frame *) client_data; + struct device *d = XDEVICE (FRAME_DEVICE (f)); Lisp_Object tail; - struct frame *target_frame = NULL; - LIST_LOOP (tail, frame_list) + DEVICE_FRAME_LOOP (tail, d) { - if (target_frame = XFRAME (XCAR (tail))) + struct frame *target_frame = XFRAME (XCAR (tail)); + if (FRAME_X_XIC (target_frame)) { - if ( FRAME_X_XIC(target_frame) ) - { - XDestroyIC (FRAME_X_XIC(target_frame)); - FRAME_X_XIC (target_frame) = NULL; - } + XDestroyIC (FRAME_X_XIC (target_frame)); + FRAME_X_XIC (target_frame) = NULL; } } @@ -176,10 +172,10 @@ static void IMInstantiateCallback (Display *dpy, XPointer client_data, XPointer call_data) { - struct frame *f = (struct frame *)client_data; - struct device *d = XDEVICE (FRAME_DEVICE ((struct frame *)client_data)); + struct frame *f = (struct frame *) client_data; + struct device *d = XDEVICE (FRAME_DEVICE (f)); XIM xim; - Widget w = FRAME_X_TEXT_WIDGET ((struct frame *)client_data); + Widget w = FRAME_X_TEXT_WIDGET (f); Window win = XtWindow (w); XRectangle p_area = {0,0,1,1}, s_area = {0,0,1,1}; XPoint spot = {0,0}; @@ -225,7 +221,7 @@ /* destroy callback for im */ ximcallback.callback = IMDestroyCallback; - ximcallback.client_data = (XPointer)f; + ximcallback.client_data = (XPointer) f; XSetIMValues (xim, XNDestroyCallback, &ximcallback, NULL); } else @@ -311,16 +307,16 @@ static void XIM_delete_frame (Widget w, XtPointer client_data, XtPointer call_data) { - struct frame *f = (struct frame *)client_data; - struct device *d = XDEVICE (FRAME_DEVICE ((struct frame *)client_data)); + struct frame *f = (struct frame *) client_data; + struct device *d = XDEVICE (FRAME_DEVICE (f)); Display *dpy = DEVICE_X_DISPLAY (d); XUnregisterIMInstantiateCallback (dpy, NULL, NULL, NULL, - IMInstantiateCallback, (XtPointer)f); + IMInstantiateCallback, (XPointer) f); - if ( FRAME_X_XIC (f) ) + if (FRAME_X_XIC (f)) { - XDestroyIC (FRAME_X_XIC(f)); + XDestroyIC (FRAME_X_XIC (f)); FRAME_X_XIC (f) = NULL; } return; @@ -335,7 +331,7 @@ struct device *d = XDEVICE (FRAME_DEVICE (f)); XRegisterIMInstantiateCallback (DEVICE_X_DISPLAY (d), NULL, NULL, NULL, - IMInstantiateCallback, (XtPointer)f); + IMInstantiateCallback, (XPointer) f); #if 0 if ( FRAME_X_XIC (f) ) diff -r 28d9c139be4c -r 11054d720c21 src/insdel.c --- a/src/insdel.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/insdel.c Mon Aug 13 11:26:11 2007 +0200 @@ -3234,7 +3234,7 @@ /************************************************************************/ void -vars_of_insdel (void) +reinit_vars_of_insdel (void) { int i; @@ -3246,6 +3246,12 @@ } void +vars_of_insdel (void) +{ + reinit_vars_of_insdel (); +} + +void init_buffer_text (struct buffer *b) { if (!b->base_buffer) diff -r 28d9c139be4c -r 11054d720c21 src/insdel.h --- a/src/insdel.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/insdel.h Mon Aug 13 11:26:11 2007 +0200 @@ -140,11 +140,11 @@ /************************************************************************/ Memind do_marker_adjustment (Memind mpos, Memind from, - Memind to, int amount); + Memind to, Bytecount amount); void fixup_internal_substring (CONST Bufbyte *nonreloc, Lisp_Object reloc, - int offset, int *len); + Bytecount offset, Bytecount *len); /* In font-lock.c */ void font_lock_maybe_update_syntactic_caches (struct buffer *buf, diff -r 28d9c139be4c -r 11054d720c21 src/intl.c --- a/src/intl.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/intl.c Mon Aug 13 11:26:11 2007 +0200 @@ -165,7 +165,6 @@ #endif /* I18N4 */ -Lisp_Object Qdomain; Lisp_Object Qdefer_gettext; DEFUN ("ignore-defer-gettext", Fignore_defer_gettext, 1, 1, 0, /* @@ -274,14 +273,7 @@ { CHECK_STRING (domain_name); if (load_in_progress) - { -#ifdef I18N3 - Vfile_domain = Fpurecopy (domain_name); - return Vfile_domain; -#else - return (domain_name); -#endif - } + return (domain_name); else return Qnil; } @@ -307,8 +299,6 @@ void syms_of_intl (void) { - defsymbol (&Qdomain, "domain"); - /* defer-gettext is defined as a symbol because when it is used in menu specification strings, it is not evaluated as a function by menu_item_descriptor_to_widget_value(). */ diff -r 28d9c139be4c -r 11054d720c21 src/keymap.c --- a/src/keymap.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/keymap.c Mon Aug 13 11:26:11 2007 +0200 @@ -252,15 +252,15 @@ /************************************************************************/ static Lisp_Object -mark_keymap (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_keymap (Lisp_Object obj) { Lisp_Keymap *keymap = XKEYMAP (obj); - markobj (keymap->parents); - markobj (keymap->prompt); - markobj (keymap->inverse_table); - markobj (keymap->sub_maps_cache); - markobj (keymap->default_binding); - markobj (keymap->name); + mark_object (keymap->parents); + mark_object (keymap->prompt); + mark_object (keymap->inverse_table); + mark_object (keymap->sub_maps_cache); + mark_object (keymap->default_binding); + mark_object (keymap->name); return keymap->table; } @@ -278,7 +278,7 @@ print_internal (keymap->name, printcharfun, 1); /* #### Yuck! This is no way to form plural! --hniksic */ sprintf (buf, "%s%d entr%s 0x%x>", - ((NILP (keymap->name)) ? "" : " "), + (NILP (keymap->name) ? "" : " "), size, ((size == 1) ? "y" : "ies"), keymap->header.uid); @@ -1351,6 +1351,8 @@ *keysym = QKescape; else if (EQ (*keysym, QDEL)) *keysym = QKdelete; + else if (EQ (*keysym, QSPC)) + *keysym = QKspace; else if (EQ (*keysym, QBS)) *keysym = QKbackspace; /* Emacs compatibility */ @@ -3175,9 +3177,9 @@ for (i = 0; i < size; i++) { Lisp_Object s2 = Fsingle_key_description - (((STRINGP (keys)) - ? make_char (string_char (XSTRING (keys), i)) - : XVECTOR_DATA (keys)[i])); + (STRINGP (keys) + ? make_char (string_char (XSTRING (keys), i)) + : XVECTOR_DATA (keys)[i]); if (i == 0) string = s2; @@ -3534,7 +3536,7 @@ for (;;) /* loop over all keys that match */ { - Lisp_Object k = ((CONSP (keys)) ? XCAR (keys) : keys); + Lisp_Object k = CONSP (keys) ? XCAR (keys) : keys; int i; so_far [keys_count].keysym = k; @@ -4274,6 +4276,7 @@ defsymbol (&QRET, "RET"); defsymbol (&QESC, "ESC"); defsymbol (&QDEL, "DEL"); + defsymbol (&QSPC, "SPC"); defsymbol (&QBS, "BS"); } @@ -4327,7 +4330,7 @@ staticpro (&Vcurrent_global_map); - Vsingle_space_string = make_string_nocopy ((CONST Bufbyte *) " ", 1); + Vsingle_space_string = make_string ((CONST Bufbyte *) " ", 1); staticpro (&Vsingle_space_string); } diff -r 28d9c139be4c -r 11054d720c21 src/keymap.h --- a/src/keymap.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/keymap.h Mon Aug 13 11:26:11 2007 +0200 @@ -28,7 +28,6 @@ #define XKEYMAP(x) XRECORD (x, keymap, struct Lisp_Keymap) #define XSETKEYMAP(x, p) XSETRECORD (x, p, keymap) #define KEYMAPP(x) RECORDP (x, keymap) -#define GC_KEYMAPP(x) GC_RECORDP (x, keymap) #define CHECK_KEYMAP(x) CHECK_RECORD (x, keymap) #define CONCHECK_KEYMAP(x) CONCHECK_RECORD (x, keymap) diff -r 28d9c139be4c -r 11054d720c21 src/linuxplay.c --- a/src/linuxplay.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/linuxplay.c Mon Aug 13 11:26:11 2007 +0200 @@ -125,7 +125,7 @@ /* Use a global buffer as scratch-pad for possible conversions of the sampling format */ -unsigned char linuxplay_sndbuf[SNDBUFSZ]; +static unsigned char linuxplay_sndbuf[SNDBUFSZ]; static int mix_fd; static int audio_vol; diff -r 28d9c139be4c -r 11054d720c21 src/lisp-disunion.h --- a/src/lisp-disunion.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/lisp-disunion.h Mon Aug 13 11:26:11 2007 +0200 @@ -70,8 +70,8 @@ XUINT The value bits of a Lisp_Object storing an integer, unsigned INTP Non-zero if this Lisp_Object an integer? Qzero Lisp Integer 0 - EQ Non-zero if two Lisp_Objects are identical - GC_EQ Version of EQ used during garbage collection */ + EQ Non-zero if two Lisp_Objects are identical */ + typedef EMACS_INT Lisp_Object; @@ -83,14 +83,16 @@ #define XTYPE(x) ((enum Lisp_Type) (((EMACS_UINT)(x)) & ~VALMASK)) #define XPNTRVAL(x) (x) /* This depends on Lisp_Type_Record == 0 */ #define XCHARVAL(x) ((x) >> GCBITS) -#define GC_EQ(x,y) EQ (x,y) #define XREALINT(x) ((x) >> INT_GCBITS) #define XUINT(x) ((EMACS_UINT)(x) >> INT_GCBITS) #define INTP(x) ((EMACS_UINT)(x) & Lisp_Type_Int_Bit) +#define INT_PLUS(x,y) ((x)+(y)-Lisp_Type_Int_Bit) +#define INT_MINUS(x,y) ((x)-(y)+Lisp_Type_Int_Bit) +#define INT_PLUS1(x) INT_PLUS (x, make_int (1)) +#define INT_MINUS1(x) INT_MINUS (x, make_int (1)) #define Qzero make_int (0) #define Qnull_pointer ((Lisp_Object) 0) -#define XGCTYPE(x) XTYPE(x) #define EQ(x,y) ((x) == (y)) #define XSETINT(var, value) ((void) ((var) = make_int (value))) #define XSETCHAR(var, value) ((void) ((var) = make_char (value))) diff -r 28d9c139be4c -r 11054d720c21 src/lisp-union.h --- a/src/lisp-union.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/lisp-union.h Mon Aug 13 11:26:11 2007 +0200 @@ -123,11 +123,13 @@ #define XREALINT(x) ((x).s.val) #define XUINT(x) ((x).u.val) #define XTYPE(x) ((x).gu.type) -#define XGCTYPE(x) XTYPE (x) #define EQ(x,y) ((x).v == (y).v) #define INTP(x) ((x).s.bits) -#define GC_EQ(x,y) EQ (x, y) +#define INT_PLUS(x,y) make_int (XINT (x) + XINT (y)) +#define INT_MINUS(x,y) make_int (XINT (x) - XINT (y)) +#define INT_PLUS1(x) make_int (XINT (x) + 1) +#define INT_MINUS1(x) make_int (XINT (x) - 1) /* Convert between a (void *) and a Lisp_Object, as when the Lisp_Object is passed to a toolkit callback function */ diff -r 28d9c139be4c -r 11054d720c21 src/lisp.h --- a/src/lisp.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/lisp.h Mon Aug 13 11:26:11 2007 +0200 @@ -250,6 +250,33 @@ /*#define REGISTER register*/ /*#endif*/ + +/* EMACS_INT is the underlying integral type into which a Lisp_Object must fit. + In particular, it must be large enough to contain a pointer. + config.h can override this, e.g. to use `long long' for bigger lisp ints. */ + +#ifndef SIZEOF_EMACS_INT +# define SIZEOF_EMACS_INT SIZEOF_VOID_P +#endif + +#ifndef EMACS_INT +# if SIZEOF_EMACS_INT == SIZEOF_LONG +# define EMACS_INT long +# elif SIZEOF_EMACS_INT == SIZEOF_INT +# define EMACS_INT int +# elif SIZEOF_EMACS_INT == SIZEOF_LONG_LONG +# define EMACS_INT long long +# else +# error Unable to determine suitable type for EMACS_INT +# endif +#endif + +#ifndef EMACS_UINT +# define EMACS_UINT unsigned EMACS_INT +#endif + +#define BITS_PER_EMACS_INT (SIZEOF_EMACS_INT * BITS_PER_CHAR) + /************************************************************************/ /* typedefs */ @@ -284,17 +311,17 @@ buffer.h (where they rightfully belong) to avoid syntax errors in function prototypes. */ -typedef int Bufpos; -typedef int Bytind; -typedef int Memind; +typedef EMACS_INT Bufpos; +typedef EMACS_INT Bytind; +typedef EMACS_INT Memind; /* Counts of bytes or chars */ -typedef int Bytecount; -typedef int Charcount; +typedef EMACS_INT Bytecount; +typedef EMACS_INT Charcount; /* Length in bytes of a string in external format */ -typedef int Extcount; +typedef EMACS_INT Extcount; typedef struct lstream Lstream; @@ -340,6 +367,8 @@ struct Lisp_Gui_Item; typedef struct Lisp_Gui_Item Lisp_Gui_Item; struct display_line; +struct display_glyph_area; +struct display_box; struct redisplay_info; struct window_mirror; struct scrollbar_instance; @@ -467,6 +496,14 @@ }; #endif +enum edge_style +{ + EDGE_ETCHED_IN, + EDGE_ETCHED_OUT, + EDGE_BEVEL_IN, + EDGE_BEVEL_OUT +}; + #ifndef ERROR_CHECK_TYPECHECK typedef enum error_behavior @@ -523,32 +560,6 @@ #define POINTER_TYPE_P(type) ((type) == Lisp_Type_Record) -/* EMACS_INT is the underlying integral type into which a Lisp_Object must fit. - In particular, it must be large enough to contain a pointer. - config.h can override this, e.g. to use `long long' for bigger lisp ints. */ - -#ifndef SIZEOF_EMACS_INT -# define SIZEOF_EMACS_INT SIZEOF_VOID_P -#endif - -#ifndef EMACS_INT -# if SIZEOF_EMACS_INT == SIZEOF_LONG -# define EMACS_INT long -# elif SIZEOF_EMACS_INT == SIZEOF_INT -# define EMACS_INT int -# elif SIZEOF_EMACS_INT == SIZEOF_LONG_LONG -# define EMACS_INT long long -# else -# error Unable to determine suitable type for EMACS_INT -# endif -#endif - -#ifndef EMACS_UINT -# define EMACS_UINT unsigned EMACS_INT -#endif - -#define BITS_PER_EMACS_INT (SIZEOF_EMACS_INT * BITS_PER_CHAR) - /* Overridden by m/next.h */ #ifndef ASSERT_VALID_POINTER # define ASSERT_VALID_POINTER(pnt) (assert ((((EMACS_UINT) pnt) & 3) == 0)) @@ -569,7 +580,7 @@ # include "lisp-disunion.h" #endif /* !USE_UNION_TYPE */ -#define XPNTR(x) ((void *) (XPNTRVAL(x))) +#define XPNTR(x) ((void *) XPNTRVAL(x)) /* WARNING WARNING WARNING. You must ensure on your own that proper GC protection is provided for the elements in this array. */ @@ -581,8 +592,8 @@ /* Close your eyes now lest you vomit or spontaneously combust ... */ #define HACKEQ_UNSAFE(obj1, obj2) \ - (EQ (obj1, obj2) || (!POINTER_TYPE_P (XGCTYPE (obj1)) \ - && !POINTER_TYPE_P (XGCTYPE (obj2)) \ + (EQ (obj1, obj2) || (!POINTER_TYPE_P (XTYPE (obj1)) \ + && !POINTER_TYPE_P (XTYPE (obj2)) \ && XCHAR_OR_INT (obj1) == XCHAR_OR_INT (obj2))) #ifdef DEBUG_XEMACS @@ -612,7 +623,6 @@ to mean "no such value". */ #define UNBOUNDP(val) EQ (val, Qunbound) -#define GC_UNBOUNDP(val) GC_EQ (val, Qunbound) /*********** cons ***********/ @@ -641,7 +651,6 @@ #define XCONS(x) XRECORD (x, cons, Lisp_Cons) #define XSETCONS(x, p) XSETRECORD (x, p, cons) #define CONSP(x) RECORDP (x, cons) -#define GC_CONSP(x) GC_RECORDP (x, cons) #define CHECK_CONS(x) CHECK_RECORD (x, cons) #define CONCHECK_CONS(x) CONCHECK_RECORD (x, cons) @@ -651,7 +660,6 @@ extern Lisp_Object Qnil; #define NILP(x) EQ (x, Qnil) -#define GC_NILP(x) GC_EQ (x, Qnil) #define XCAR(a) (XCONS (a)->car) #define XCDR(a) (XCONS (a)->cdr) #define LISTP(x) (CONSP(x) || NILP(x)) @@ -711,7 +719,7 @@ #define EXTERNAL_LIST_LOOP_DELETE_IF(elt, list, condition) do { \ Lisp_Object prev_tail_##list = Qnil; \ Lisp_Object tail_##list; \ - int len_##list; \ + EMACS_INT len_##list; \ EXTERNAL_LIST_LOOP_4 (elt, list, tail_##list, len_##list) \ { \ if (condition) \ @@ -768,26 +776,26 @@ #define EXTERNAL_LIST_LOOP_1(list) \ Lisp_Object ELL1_elt, ELL1_hare, ELL1_tortoise; \ -int ELL1_len; \ -EXTERNAL_LIST_LOOP_6(ELL1_elt, list, ELL1_len, ELL1_hare, \ - ELL1_tortoise, CIRCULAR_LIST_SUSPICION_LENGTH) +EMACS_INT ELL1_len; \ +EXTERNAL_LIST_LOOP_6 (ELL1_elt, list, ELL1_len, ELL1_hare, \ + ELL1_tortoise, CIRCULAR_LIST_SUSPICION_LENGTH) #define EXTERNAL_LIST_LOOP_2(elt, list) \ Lisp_Object hare_##elt, tortoise_##elt; \ -int len_##elt; \ -EXTERNAL_LIST_LOOP_6(elt, list, len_##elt, hare_##elt, \ - tortoise_##elt, CIRCULAR_LIST_SUSPICION_LENGTH) +EMACS_INT len_##elt; \ +EXTERNAL_LIST_LOOP_6 (elt, list, len_##elt, hare_##elt, \ + tortoise_##elt, CIRCULAR_LIST_SUSPICION_LENGTH) #define EXTERNAL_LIST_LOOP_3(elt, list, tail) \ Lisp_Object tortoise_##elt; \ -int len_##elt; \ -EXTERNAL_LIST_LOOP_6(elt, list, len_##elt, tail, \ - tortoise_##elt, CIRCULAR_LIST_SUSPICION_LENGTH) +EMACS_INT len_##elt; \ +EXTERNAL_LIST_LOOP_6 (elt, list, len_##elt, tail, \ + tortoise_##elt, CIRCULAR_LIST_SUSPICION_LENGTH) #define EXTERNAL_LIST_LOOP_4(elt, list, tail, len) \ Lisp_Object tortoise_##elt; \ -EXTERNAL_LIST_LOOP_6(elt, list, len, tail, \ - tortoise_##elt, CIRCULAR_LIST_SUSPICION_LENGTH) +EXTERNAL_LIST_LOOP_6 (elt, list, len, tail, \ + tortoise_##elt, CIRCULAR_LIST_SUSPICION_LENGTH) #define EXTERNAL_LIST_LOOP_6(elt, list, len, hare, \ @@ -812,30 +820,30 @@ /* Optimized and safe macros for looping over external alists. */ -#define EXTERNAL_ALIST_LOOP_4(elt, elt_car, elt_cdr, list) \ -Lisp_Object hare_##elt, tortoise_##elt; \ -int len_##elt; \ -EXTERNAL_ALIST_LOOP_8 (elt, elt_car, elt_cdr, list, \ - len_##elt, hare_##elt, tortoise_##elt, \ +#define EXTERNAL_ALIST_LOOP_4(elt, elt_car, elt_cdr, list) \ +Lisp_Object hare_##elt, tortoise_##elt; \ +EMACS_INT len_##elt; \ +EXTERNAL_ALIST_LOOP_8 (elt, elt_car, elt_cdr, list, \ + len_##elt, hare_##elt, tortoise_##elt, \ CIRCULAR_LIST_SUSPICION_LENGTH) #define EXTERNAL_ALIST_LOOP_5(elt, elt_car, elt_cdr, list, tail) \ Lisp_Object tortoise_##elt; \ -int len_##elt; \ -EXTERNAL_ALIST_LOOP_8(elt, elt_car, elt_cdr, list, \ - len_##elt, tail, tortoise_##elt, \ - CIRCULAR_LIST_SUSPICION_LENGTH) +EMACS_INT len_##elt; \ +EXTERNAL_ALIST_LOOP_8 (elt, elt_car, elt_cdr, list, \ + len_##elt, tail, tortoise_##elt, \ + CIRCULAR_LIST_SUSPICION_LENGTH) \ #define EXTERNAL_ALIST_LOOP_6(elt, elt_car, elt_cdr, list, tail, len) \ Lisp_Object tortoise_##elt; \ -EXTERNAL_ALIST_LOOP_8(elt, elt_car, elt_cdr, list, \ - len, tail, tortoise_##elt, \ - CIRCULAR_LIST_SUSPICION_LENGTH) +EXTERNAL_ALIST_LOOP_8 (elt, elt_car, elt_cdr, list, \ + len, tail, tortoise_##elt, \ + CIRCULAR_LIST_SUSPICION_LENGTH) #define EXTERNAL_ALIST_LOOP_8(elt, elt_car, elt_cdr, list, len, hare, \ tortoise, suspicion_length) \ -EXTERNAL_LIST_LOOP_6(elt, list, len, hare, tortoise, suspicion_length) \ +EXTERNAL_LIST_LOOP_6 (elt, list, len, hare, tortoise, suspicion_length) \ if (CONSP (elt) ? (elt_car = XCAR (elt), elt_cdr = XCDR (elt), 0) :1) \ continue; \ else @@ -844,20 +852,20 @@ /* Optimized and safe macros for looping over external property lists. */ #define EXTERNAL_PROPERTY_LIST_LOOP_3(key, value, list) \ Lisp_Object key, value, hare_##key, tortoise_##key; \ -int len_##key; \ -EXTERNAL_PROPERTY_LIST_LOOP_7(key, value, list, len_##key, hare_##key,\ +EMACS_INT len_##key; \ +EXTERNAL_PROPERTY_LIST_LOOP_7 (key, value, list, len_##key, hare_##key, \ tortoise_##key, CIRCULAR_LIST_SUSPICION_LENGTH) #define EXTERNAL_PROPERTY_LIST_LOOP_4(key, value, list, tail) \ Lisp_Object key, value, tail, tortoise_##key; \ -int len_##key; \ -EXTERNAL_PROPERTY_LIST_LOOP_7(key, value, list, len_##key, tail, \ +EMACS_INT len_##key; \ +EXTERNAL_PROPERTY_LIST_LOOP_7 (key, value, list, len_##key, tail, \ tortoise_##key, CIRCULAR_LIST_SUSPICION_LENGTH) #define EXTERNAL_PROPERTY_LIST_LOOP_5(key, value, list, tail, len) \ Lisp_Object key, value, tail, tortoise_##key; \ -int len; \ -EXTERNAL_PROPERTY_LIST_LOOP_7(key, value, list, len, tail, \ +EMACS_INT len; \ +EXTERNAL_PROPERTY_LIST_LOOP_7 (key, value, list, len, tail, \ tortoise_##key, CIRCULAR_LIST_SUSPICION_LENGTH) @@ -914,7 +922,7 @@ TRUE_LIST_P (Lisp_Object object) { Lisp_Object hare, tortoise; - int len; + EMACS_INT len; for (hare = tortoise = object, len = 0; CONSP (hare); @@ -936,7 +944,7 @@ #define CHECK_TRUE_LIST(list) do { \ Lisp_Object CTL_list = (list); \ Lisp_Object CTL_hare, CTL_tortoise; \ - int CTL_len; \ + EMACS_INT CTL_len; \ \ for (CTL_hare = CTL_tortoise = CTL_list, CTL_len = 0; \ CONSP (CTL_hare); \ @@ -970,7 +978,6 @@ #define XSTRING(x) XRECORD (x, string, Lisp_String) #define XSETSTRING(x, p) XSETRECORD (x, p, string) #define STRINGP(x) RECORDP (x, string) -#define GC_STRINGP(x) GC_RECORDP (x, string) #define CHECK_STRING(x) CHECK_RECORD (x, string) #define CONCHECK_STRING(x) CONCHECK_RECORD (x, string) @@ -1039,7 +1046,6 @@ #define XVECTOR(x) XRECORD (x, vector, Lisp_Vector) #define XSETVECTOR(x, p) XSETRECORD (x, p, vector) #define VECTORP(x) RECORDP (x, vector) -#define GC_VECTORP(x) GC_RECORDP (x, vector) #define CHECK_VECTOR(x) CHECK_RECORD (x, vector) #define CONCHECK_VECTOR(x) CONCHECK_RECORD (x, vector) @@ -1078,12 +1084,10 @@ #define XBIT_VECTOR(x) XRECORD (x, bit_vector, Lisp_Bit_Vector) #define XSETBIT_VECTOR(x, p) XSETRECORD (x, p, bit_vector) #define BIT_VECTORP(x) RECORDP (x, bit_vector) -#define GC_BIT_VECTORP(x) GC_RECORDP (x, bit_vector) #define CHECK_BIT_VECTOR(x) CHECK_RECORD (x, bit_vector) #define CONCHECK_BIT_VECTOR(x) CONCHECK_RECORD (x, bit_vector) #define BITP(x) (INTP (x) && (XINT (x) == 0 || XINT (x) == 1)) -#define GC_BITP(x) (GC_INTP (x) && (XINT (x) == 0 || XINT (x) == 1)) #define CHECK_BIT(x) do { \ if (!BITP (x)) \ @@ -1098,25 +1102,22 @@ #define bit_vector_length(v) ((v)->size) #define bit_vector_next(v) ((v)->next) -INLINE int bit_vector_bit (Lisp_Bit_Vector *v, int i); +INLINE int bit_vector_bit (Lisp_Bit_Vector *v, size_t n); INLINE int -bit_vector_bit (Lisp_Bit_Vector *v, int i) +bit_vector_bit (Lisp_Bit_Vector *v, size_t n) { - unsigned int ui = (unsigned int) i; - - return (((v)->bits[ui >> LONGBITS_LOG2] >> (ui & (LONGBITS_POWER_OF_2 - 1))) + return ((v->bits[n >> LONGBITS_LOG2] >> (n & (LONGBITS_POWER_OF_2 - 1))) & 1); } -INLINE void set_bit_vector_bit (Lisp_Bit_Vector *v, int i, int value); +INLINE void set_bit_vector_bit (Lisp_Bit_Vector *v, size_t n, int value); INLINE void -set_bit_vector_bit (Lisp_Bit_Vector *v, int i, int value) +set_bit_vector_bit (Lisp_Bit_Vector *v, size_t n, int value) { - unsigned int ui = (unsigned int) i; if (value) - (v)->bits[ui >> LONGBITS_LOG2] |= (1UL << (ui & (LONGBITS_POWER_OF_2 - 1))); + v->bits[n >> LONGBITS_LOG2] |= (1UL << (n & (LONGBITS_POWER_OF_2 - 1))); else - (v)->bits[ui >> LONGBITS_LOG2] &= ~(1UL << (ui & (LONGBITS_POWER_OF_2 - 1))); + v->bits[n >> LONGBITS_LOG2] &= ~(1UL << (n & (LONGBITS_POWER_OF_2 - 1))); } /* Number of longs required to hold LEN bits */ @@ -1149,7 +1150,6 @@ #define XSYMBOL(x) XRECORD (x, symbol, Lisp_Symbol) #define XSETSYMBOL(x, p) XSETRECORD (x, p, symbol) #define SYMBOLP(x) RECORDP (x, symbol) -#define GC_SYMBOLP(x) GC_RECORDP (x, symbol) #define CHECK_SYMBOL(x) CHECK_RECORD (x, symbol) #define CONCHECK_SYMBOL(x) CONCHECK_RECORD (x, symbol) @@ -1178,7 +1178,6 @@ #define XSUBR(x) XRECORD (x, subr, Lisp_Subr) #define XSETSUBR(x, p) XSETRECORD (x, p, subr) #define SUBRP(x) RECORDP (x, subr) -#define GC_SUBRP(x) GC_RECORDP (x, subr) #define CHECK_SUBR(x) CHECK_RECORD (x, subr) #define CONCHECK_SUBR(x) CONCHECK_RECORD (x, subr) @@ -1201,7 +1200,6 @@ #define XMARKER(x) XRECORD (x, marker, Lisp_Marker) #define XSETMARKER(x, p) XSETRECORD (x, p, marker) #define MARKERP(x) RECORDP (x, marker) -#define GC_MARKERP(x) GC_RECORDP (x, marker) #define CHECK_MARKER(x) CHECK_RECORD (x, marker) #define CONCHECK_MARKER(x) CONCHECK_RECORD (x, marker) @@ -1214,7 +1212,6 @@ /*********** char ***********/ #define CHARP(x) (XTYPE (x) == Lisp_Type_Char) -#define GC_CHARP(x) (XGCTYPE (x) == Lisp_Type_Char) #ifdef ERROR_CHECK_TYPECHECK @@ -1256,7 +1253,6 @@ #define XFLOAT(x) XRECORD (x, float, Lisp_Float) #define XSETFLOAT(x, p) XSETRECORD (x, p, float) #define FLOATP(x) RECORDP (x, float) -#define GC_FLOATP(x) GC_RECORDP (x, float) #define CHECK_FLOAT(x) CHECK_RECORD (x, float) #define CONCHECK_FLOAT(x) CONCHECK_RECORD (x, float) @@ -1276,31 +1272,25 @@ } while (0) # define INT_OR_FLOATP(x) (INTP (x) || FLOATP (x)) -# define GC_INT_OR_FLOATP(x) (GC_INTP (x) || GC_FLOATP (x)) #else /* not LISP_FLOAT_TYPE */ #define XFLOAT(x) --- error! No float support. --- #define XSETFLOAT(x, p) --- error! No float support. --- #define FLOATP(x) 0 -#define GC_FLOATP(x) 0 #define CHECK_FLOAT(x) --- error! No float support. --- #define CONCHECK_FLOAT(x) --- error! No float support. --- #define XFLOATINT(n) XINT(n) #define CHECK_INT_OR_FLOAT CHECK_INT #define CONCHECK_INT_OR_FLOAT CONCHECK_INT -#define INT_OR_FLOATP(x) (INTP (x)) -# define GC_INT_OR_FLOATP(x) (GC_INTP (x)) +#define INT_OR_FLOATP(x) INTP (x) #endif /* not LISP_FLOAT_TYPE */ /*********** int ***********/ -#define GC_INTP(x) INTP (x) - #define ZEROP(x) EQ (x, Qzero) -#define GC_ZEROP(x) GC_EQ (x, Qzero) #ifdef ERROR_CHECK_TYPECHECK @@ -1338,7 +1328,6 @@ } while (0) #define NATNUMP(x) (INTP (x) && XINT (x) >= 0) -#define GC_NATNUMP(x) (GC_INTP (x) && XINT (x) >= 0) #define CHECK_NATNUM(x) do { \ if (!NATNUMP (x)) \ @@ -1460,7 +1449,6 @@ #define XWEAK_LIST(x) XRECORD (x, weak_list, struct weak_list) #define XSETWEAK_LIST(x, p) XSETRECORD (x, p, weak_list) #define WEAK_LISTP(x) RECORDP (x, weak_list) -#define GC_WEAK_LISTP(x) GC_RECORDP (x, weak_list) #define CHECK_WEAK_LIST(x) CHECK_RECORD (x, weak_list) #define CONCHECK_WEAK_LIST(x) CONCHECK_RECORD (x, weak_list) @@ -1469,9 +1457,8 @@ Lisp_Object make_weak_list (enum weak_list_type type); /* The following two are only called by the garbage collector */ -int finish_marking_weak_lists (int (*obj_marked_p) (Lisp_Object), - void (*markobj) (Lisp_Object)); -void prune_weak_lists (int (*obj_marked_p) (Lisp_Object)); +int finish_marking_weak_lists (void); +void prune_weak_lists (void); /*********** lcrecord lists ***********/ @@ -1487,7 +1474,6 @@ #define XLCRECORD_LIST(x) XRECORD (x, lcrecord_list, struct lcrecord_list) #define XSETLCRECORD_LIST(x, p) XSETRECORD (x, p, lcrecord_list) #define LCRECORD_LISTP(x) RECORDP (x, lcrecord_list) -#define GC_LCRECORD_LISTP(x) GC_RECORDP (x, lcrecord_list) /* #define CHECK_LCRECORD_LIST(x) CHECK_RECORD (x, lcrecord_list) Lcrecord lists should never escape to the Lisp level, so functions should not be doing this. */ @@ -1814,8 +1800,7 @@ gcpro4.next = &gcpro3, gcpro4.var = &var4, gcpro4.nvars = 1, \ gcprolist = &gcpro4 )) -#define GCPRO5(var1, var2, var3, var4, var5) \ - ((void) ( \ +#define GCPRO5(var1, var2, var3, var4, var5) ((void) ( \ gcpro1.next = gcprolist, gcpro1.var = &var1, gcpro1.nvars = 1, \ gcpro2.next = &gcpro1, gcpro2.var = &var2, gcpro2.nvars = 1, \ gcpro3.next = &gcpro2, gcpro3.var = &var3, gcpro3.nvars = 1, \ @@ -1847,8 +1832,7 @@ ngcpro4.next = &ngcpro3, ngcpro4.var = &var4, ngcpro4.nvars = 1, \ gcprolist = &ngcpro4 )) -#define NGCPRO5(var1, var2, var3, var4, var5) \ - ((void) ( \ +#define NGCPRO5(var1, var2, var3, var4, var5) ((void) ( \ ngcpro1.next = gcprolist, ngcpro1.var = &var1, ngcpro1.nvars = 1, \ ngcpro2.next = &ngcpro1, ngcpro2.var = &var2, ngcpro2.nvars = 1, \ ngcpro3.next = &ngcpro2, ngcpro3.var = &var3, ngcpro3.nvars = 1, \ @@ -1880,8 +1864,7 @@ nngcpro4.next = &nngcpro3, nngcpro4.var = &var4, nngcpro4.nvars = 1, \ gcprolist = &nngcpro4 )) -#define NNGCPRO5(var1, var2, var3, var4, var5) \ - ((void) ( \ +#define NNGCPRO5(var1, var2, var3, var4, var5) ((void) ( \ nngcpro1.next = gcprolist, nngcpro1.var = &var1, nngcpro1.nvars = 1, \ nngcpro2.next = &nngcpro1, nngcpro2.var = &var2, nngcpro2.nvars = 1, \ nngcpro3.next = &nngcpro2, nngcpro3.var = &var3, nngcpro3.nvars = 1, \ @@ -1943,6 +1926,21 @@ /* Call staticpro (&var) to protect static variable `var'. */ void staticpro (Lisp_Object *); +/* Call staticpro_nodump (&var) to protect static variable `var'. */ +/* var will not be saved at dump time */ +void staticpro_nodump (Lisp_Object *); + +/* Call dumpstruct(&var, &desc) to dump the structure pointed to by `var'. */ +void dumpstruct (void *, const struct struct_description *); + +/* Call pdump_wire(&var) to ensure that var is properly updated after pdump. */ +void pdump_wire (Lisp_Object *); + +/* Call pdump_wire(&var) to ensure that var is properly updated after + pdump. var must point to a linked list of objects out of which + some may not be dumped */ +void pdump_wire_list (Lisp_Object *); + /* Nonzero means Emacs has already been initialized. Used during startup to detect startup of dumped Emacs. */ extern int initialized; @@ -1992,7 +1990,7 @@ #endif #endif #ifndef IS_ANY_SEP -#define IS_ANY_SEP(c) (IS_DIRECTORY_SEP (c)) +#define IS_ANY_SEP(c) IS_DIRECTORY_SEP (c) #endif #ifdef HAVE_INTTYPES_H @@ -2056,11 +2054,22 @@ void mark_conses_in_list (Lisp_Object); void free_marker (Lisp_Marker *); int object_dead_p (Lisp_Object); +void mark_object (Lisp_Object obj); +int marked_p (Lisp_Object obj); #ifdef MEMORY_USAGE_STATS size_t malloced_storage_size (void *, size_t, struct overhead_stats *); size_t fixed_type_block_overhead (size_t); #endif +#ifdef PDUMP +void pdump (void); +int pdump_load (void); + +extern char *pdump_start, *pdump_end; +#define DUMPEDP(adr) ((((char *)(adr)) < pdump_end) && (((char *)(adr)) >= pdump_start)) +#else +#define DUMPEDP(adr) 0 +#endif /* Defined in buffer.c */ Lisp_Object make_buffer (struct buffer *); @@ -2083,7 +2092,7 @@ Lisp_Object)); Lisp_Object wrong_type_argument (Lisp_Object, Lisp_Object); DECLARE_DOESNT_RETURN (dead_wrong_type_argument (Lisp_Object, Lisp_Object)); -void check_int_range (int, int, int); +void check_int_range (EMACS_INT, EMACS_INT, EMACS_INT); enum arith_comparison { arith_equal, @@ -2130,8 +2139,8 @@ Bufpos bufpos_clip_to_bounds (Bufpos, Bufpos, Bufpos); Bytind bytind_clip_to_bounds (Bytind, Bytind, Bytind); void buffer_insert1 (struct buffer *, Lisp_Object); -Lisp_Object make_string_from_buffer (struct buffer *, int, int); -Lisp_Object make_string_from_buffer_no_extents (struct buffer *, int, int); +Lisp_Object make_string_from_buffer (struct buffer *, Bufpos, Charcount); +Lisp_Object make_string_from_buffer_no_extents (struct buffer *, Bufpos, Charcount); Lisp_Object save_excursion_save (void); Lisp_Object save_restriction_save (void); Lisp_Object save_excursion_restore (Lisp_Object); @@ -2336,7 +2345,6 @@ Lisp_Object remassq_no_quit (Lisp_Object, Lisp_Object); Lisp_Object remrassq_no_quit (Lisp_Object, Lisp_Object); -void pure_put (Lisp_Object, Lisp_Object, Lisp_Object); int plists_differ (Lisp_Object, Lisp_Object, int, int, int); Lisp_Object internal_plist_get (Lisp_Object, Lisp_Object); void internal_plist_put (Lisp_Object *, Lisp_Object, Lisp_Object); @@ -2365,6 +2373,7 @@ /* Defined in indent.c */ int bi_spaces_at_point (struct buffer *, Bytind); int column_at_point (struct buffer *, Bufpos, int); +int string_column_at_point (struct Lisp_String *, Bufpos, int); int current_column (struct buffer *); void invalidate_current_column (void); Bufpos vmotion (struct window *, Bufpos, int, int *); @@ -2467,7 +2476,7 @@ void internal_object_printer (Lisp_Object, Lisp_Object, int); /* Defined in profile.c */ -void mark_profiling_info (void (*) (Lisp_Object)); +void mark_profiling_info (void); void profile_increase_call_count (Lisp_Object); extern int profiling_active; extern int profiling_redisplay_flag; @@ -2489,6 +2498,7 @@ Bufpos find_next_newline (struct buffer *, Bufpos, int); Bufpos find_next_newline_no_quit (struct buffer *, Bufpos, int); Bytind bi_find_next_newline_no_quit (struct buffer *, Bytind, int); +Bytind bi_find_next_emchar_in_string (struct Lisp_String*, Emchar, Bytind, EMACS_INT); Bufpos find_before_next_newline (struct buffer *, Bufpos, Bufpos, int); struct re_pattern_buffer *compile_pattern (Lisp_Object, struct re_registers *, char *, int, Error_behavior); @@ -2530,7 +2540,7 @@ Lisp_Object follow_past_lisp_magic); /* Defined in syntax.c */ -int scan_words (struct buffer *, int, int); +Bufpos scan_words (struct buffer *, Bufpos, int); /* Defined in undo.c */ Lisp_Object truncate_undo_list (Lisp_Object, int, int); @@ -2740,7 +2750,6 @@ EXFUN (Fprocess_status, 1); EXFUN (Fprogn, UNEVALLED); EXFUN (Fprovide, 1); -EXFUN (Fpurecopy, 1); EXFUN (Fput, 3); EXFUN (Fput_range_table, 4); EXFUN (Fput_text_property, 5); @@ -2805,14 +2814,14 @@ extern Lisp_Object Qarith_error, Qarrayp, Qassoc, Qat, Qautodetect, Qautoload; extern Lisp_Object Qbackground, Qbackground_pixmap, Qbad_variable, Qbefore; extern Lisp_Object Qbeginning_of_buffer, Qbig5, Qbinary, Qbitmap, Qbitp, Qblinking; -extern Lisp_Object Qboolean, Qbottom, Qbuffer, Qbuffer_file_coding_system; +extern Lisp_Object Qboolean, Qbottom, Qbuffer; extern Lisp_Object Qbuffer_glyph_p, Qbuffer_live_p, Qbuffer_read_only, Qbutton; extern Lisp_Object Qbyte_code, Qcall_interactively, Qcategory; extern Lisp_Object Qcategory_designator_p, Qcategory_table_value_p, Qccl, Qcdr; extern Lisp_Object Qchannel, Qchar, Qchar_or_string_p, Qcharacter, Qcharacterp; extern Lisp_Object Qchars, Qcharset_g0, Qcharset_g1, Qcharset_g2, Qcharset_g3; -extern Lisp_Object Qcircular_list, Qcircular_property_list; -extern Lisp_Object Qcoding_system_error, Qcoding_system_p; +extern Lisp_Object Qcenter, Qcircular_list, Qcircular_property_list; +extern Lisp_Object Qcoding_system_error; extern Lisp_Object Qcolor, Qcolor_pixmap_image_instance_p; extern Lisp_Object Qcolumns, Qcommand, Qcommandp, Qcompletion_ignore_case; extern Lisp_Object Qconsole, Qconsole_live_p, Qconst_specifier, Qcr, Qcritical; @@ -2829,14 +2838,14 @@ extern Lisp_Object Qfont, Qforce_g0_on_output, Qforce_g1_on_output; extern Lisp_Object Qforce_g2_on_output, Qforce_g3_on_output, Qforeground; extern Lisp_Object Qformat, Qframe, Qframe_live_p, Qfunction, Qgap_overhead; -extern Lisp_Object Qgeneric, Qgeometry, Qglobal, Qheight, Qhighlight, Qicon; +extern Lisp_Object Qgeneric, Qgeometry, Qglobal, Qheight, Qhighlight, Qhorizontal, Qicon; extern Lisp_Object Qicon_glyph_p, Qid, Qidentity, Qimage, Qinfo, Qinherit; extern Lisp_Object Qinhibit_quit, Qinhibit_read_only; extern Lisp_Object Qinput_charset_conversion, Qinteger; extern Lisp_Object Qinteger_char_or_marker_p, Qinteger_or_char_p; extern Lisp_Object Qinteger_or_marker_p, Qintegerp, Qinteractive, Qinternal; extern Lisp_Object Qinvalid_function, Qinvalid_read_syntax, Qio_error; -extern Lisp_Object Qiso2022, Qkey, Qkey_assoc, Qkeymap, Qlambda, Qleft, Qlf; +extern Lisp_Object Qiso2022, Qkey, Qkey_assoc, Qkeymap, Qlambda, Qlayout, Qleft, Qlf; extern Lisp_Object Qlist, Qlistp, Qload, Qlock_shift, Qmacro, Qmagic; extern Lisp_Object Qmalformed_list, Qmalformed_property_list; extern Lisp_Object Qmalloc_overhead, Qmark, Qmarkers; @@ -2846,10 +2855,10 @@ extern Lisp_Object Qno_ascii_cntl, Qno_ascii_eol, Qno_catch; extern Lisp_Object Qno_conversion, Qno_iso6429, Qnone, Qnot, Qnothing; extern Lisp_Object Qnothing_image_instance_p, Qnotice; -extern Lisp_Object Qnumber_char_or_marker_p, Qnumber_or_marker_p, Qnumberp; +extern Lisp_Object Qnumber_char_or_marker_p, Qnumberp; extern Lisp_Object Qobject, Qold_assoc, Qold_delete, Qold_delq, Qold_rassoc; extern Lisp_Object Qold_rassq, Qonly, Qor, Qother, Qoutput_charset_conversion; -extern Lisp_Object Qoverflow_error, Qpath, Qpoint, Qpointer, Qpointer_glyph_p; +extern Lisp_Object Qoverflow_error, Qpoint, Qpointer, Qpointer_glyph_p; extern Lisp_Object Qpointer_image_instance_p, Qpost_read_conversion; extern Lisp_Object Qpre_write_conversion, Qprint, Qprint_length; extern Lisp_Object Qprint_string_length, Qprocess, Qprogn, Qprovide, Qquit; @@ -2868,7 +2877,7 @@ extern Lisp_Object Qunbound, Qundecided, Qundefined, Qunderflow_error; extern Lisp_Object Qunderline, Qunimplemented, Quser_files_and_directories; extern Lisp_Object Qvalue_assoc, Qvalues; -extern Lisp_Object Qvariable_documentation, Qvariable_domain, Qvector; +extern Lisp_Object Qvariable_documentation, Qvariable_domain, Qvertical; extern Lisp_Object Qvoid_function, Qvoid_variable, Qwarning, Qwidth, Qwidget, Qwindow; extern Lisp_Object Qwindow_live_p, Qwindow_system, Qwrong_number_of_arguments; extern Lisp_Object Qwrong_type_argument, Qx, Qy, Qyes_or_no_p; diff -r 28d9c139be4c -r 11054d720c21 src/lread.c --- a/src/lread.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/lread.c Mon Aug 13 11:26:11 2007 +0200 @@ -443,12 +443,6 @@ Lisp_Object list = Vload_force_doc_string_list; Lisp_Object tail; int fd = XINT (XCAR (Vload_descriptor_list)); - /* NOTE: If purify_flag is true, we're in-place modifying objects that - may be in purespace (and if not, they will be). Therefore, we have - to be VERY careful to make sure that all objects that we create - are purecopied -- objects in purespace are not marked for GC, and - if we leave any impure objects inside of pure ones, we're really - screwed. */ GCPRO1 (list); /* restore the old value first just in case an error occurs. */ @@ -479,13 +473,12 @@ ivan = Fread (juan); if (!CONSP (ivan)) signal_simple_error ("invalid lazy-loaded byte code", ivan); - /* Remember to purecopy; see above. */ - XCOMPILED_FUNCTION (john)->instructions = Fpurecopy (XCAR (ivan)); + XCOMPILED_FUNCTION (john)->instructions = XCAR (ivan); /* v18 or v19 bytecode file. Need to Ebolify. */ if (XCOMPILED_FUNCTION (john)->flags.ebolified && VECTORP (XCDR (ivan))) ebolify_bytecode_constants (XCDR (ivan)); - XCOMPILED_FUNCTION (john)->constants = Fpurecopy (XCDR (ivan)); + XCOMPILED_FUNCTION (john)->constants = XCDR (ivan); NUNGCPRO; } doc = compiled_function_documentation (XCOMPILED_FUNCTION (john)); @@ -925,7 +918,7 @@ /* Map FUN over SUFFIXES, as described above. FUN will be called with a char * containing the current file name, and ARG. Mapping stops when FUN returns non-zero. */ -void +static void locate_file_map_suffixes (Lisp_Object filename, Lisp_Object suffixes, int (*fun) (char *, void *), void *arg) @@ -984,7 +977,7 @@ else { /* Case c) */ - CONST char *nsuffix = XSTRING_DATA (suffixes); + CONST char *nsuffix = (CONST char *) XSTRING_DATA (suffixes); while (1) { @@ -1947,7 +1940,6 @@ sym = Fmake_symbol ( make_string ((Bufbyte *) read_ptr, len)); else { - /* intern will purecopy pname if necessary */ Lisp_Object name = make_string ((Bufbyte *) read_ptr, len); sym = Fintern (name, Qnil); } @@ -3005,12 +2997,7 @@ i++, p++) { struct Lisp_Cons *otem = XCONS (tem); -#if 0 /* FSFmacs defun hack */ - if (read_pure) - tem = Fpurecopy (Fcar (tem)); - else -#endif - tem = Fcar (tem); + tem = Fcar (tem); *p = tem; tem = otem->cdr; free_cons (otem); @@ -3149,8 +3136,17 @@ } void +reinit_vars_of_lread (void) +{ + Vread_buffer_stream = Qnil; + staticpro_nodump (&Vread_buffer_stream); +} + +void vars_of_lread (void) { + reinit_vars_of_lread (); + DEFVAR_LISP ("values", &Vvalues /* List of values of all expressions which were read, evaluated and printed. Order is reverse chronological. @@ -3268,9 +3264,6 @@ with values saved when the image is dumped. */ staticpro (&Vload_descriptor_list); - Vread_buffer_stream = Qnil; - staticpro (&Vread_buffer_stream); - /* Initialized in init_lread. */ staticpro (&Vload_force_doc_string_list); diff -r 28d9c139be4c -r 11054d720c21 src/lrecord.h --- a/src/lrecord.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/lrecord.h Mon Aug 13 11:26:11 2007 +0200 @@ -119,8 +119,7 @@ }; /* see alloc.c for an explanation */ -Lisp_Object this_one_is_unmarkable (Lisp_Object obj, - void (*markobj) (Lisp_Object)); +Lisp_Object this_one_is_unmarkable (Lisp_Object obj); struct lrecord_implementation { @@ -134,7 +133,7 @@ recursion, so the object returned should preferably be the one with the deepest level of Lisp_Object pointers. This function can be NULL, meaning no GC marking is necessary. */ - Lisp_Object (*marker) (Lisp_Object, void (*mark_object) (Lisp_Object)); + Lisp_Object (*marker) (Lisp_Object); /* This can be NULL if the object is an lcrecord; the default_object_printer() in print.c will be used. */ void (*printer) (Lisp_Object, Lisp_Object printcharfun, int escapeflag); @@ -208,7 +207,7 @@ structure. Following values are parameters, their presence, type and number is type-dependant. - The description ends with a "XD_END" record. + The description ends with a "XD_END" or "XD_SPECIFIER_END" record. Some example descriptions : static const struct lrecord_description cons_description[] = { @@ -219,20 +218,26 @@ Which means "two lisp objects starting at the 'car' element" static const struct lrecord_description string_description[] = { - { XD_STRING_DATA, offsetof(Lisp_String, data) }, - { XD_LISP_OBJECT, offsetof(Lisp_String, plist), 1 }, + { XD_BYTECOUNT, offsetof(Lisp_String, size) }, + { XD_OPAQUE_DATA_PTR, offsetof(Lisp_String, data), XD_INDIRECT(0, 1) }, + { XD_LISP_OBJECT, offsetof(Lisp_String, plist), 1 }, { XD_END } }; - "A string data pointer at 'data', one lisp object at 'plist'" + "A pointer to string data at 'data', the size of the pointed array being the value + of the size variable plus 1, and one lisp object at 'plist'" The existing types : XD_LISP_OBJECT Lisp objects. The third element is the count. This is also the type to use for pointers to other lrecords. - XD_STRING_DATA - Pointer to string data. + XD_LO_RESET_NIL + Lisp objects which will be reset to Qnil when dumping. Useful for cleaning + up caches. + XD_LO_LINK + Link in a linked list of objects of the same type. + XD_OPAQUE_PTR Pointer to undumpable data. Must be NULL when dumping. @@ -244,6 +249,16 @@ Pointer to dumpable opaque data. Parameter is the size of the data. Pointed data must be relocatable without changes. + XD_C_STRING + Pointer to a C string. + + XD_DOC_STRING + Pointer to a doc string (C string if positive, opaque value if negative) + + XD_INT_RESET + An integer which will be reset to a given value in the dump file. + + XD_SIZE_T size_t value. Used for counts. @@ -253,30 +268,40 @@ XD_LONG long value. Used for counts. + XD_BYTECOUNT + bytecount value. Used for counts. + XD_END Special type indicating the end of the array. + XD_SPECIFIER_END + Special type indicating the end of the array for a specifier. Extra + description is going to be fetched from the specifier methods. + Special macros: - XD_INDIRECT(line) - Usable where a "count" or "size" is requested. Gives the value of the element - which is at line number 'line' in the description (count starts at zero). - - XD_PARENT_INDIRECT(line) - Same as XD_INDIRECT but the element number refers to the parent structure. - Usable only in struct descriptions. + XD_INDIRECT(line, delta) + Usable where a "count" or "size" is requested. Gives the value of + the element which is at line number 'line' in the description (count + starts at zero) and adds delta to it. */ enum lrecord_description_type { XD_LISP_OBJECT, - XD_STRING_DATA, + XD_LO_RESET_NIL, + XD_LO_LINK, XD_OPAQUE_PTR, XD_STRUCT_PTR, XD_OPAQUE_DATA_PTR, + XD_C_STRING, + XD_DOC_STRING, + XD_INT_RESET, XD_SIZE_T, XD_INT, XD_LONG, - XD_END + XD_BYTECOUNT, + XD_END, + XD_SPECIFIER_END }; struct lrecord_description { @@ -291,12 +316,16 @@ const struct lrecord_description *description; }; -#define XD_INDIRECT(count) (-1-(count)) -#define XD_PARENT_INDIRECT(count) (-1000-(count)) +#define XD_INDIRECT(val, delta) (-1-((val)|(delta<<8))) + +#define XD_IS_INDIRECT(code) (code<0) +#define XD_INDIRECT_VAL(code) ((-1-code) & 255) +#define XD_INDIRECT_DELTA(code) (((-1-code)>>8) & 255) #define XD_DYNARR_DESC(base_type, sub_desc) \ - { XD_STRUCT_PTR, offsetof(base_type, base), XD_INDIRECT(1), sub_desc }, \ - { XD_INT, offsetof(base_type, max) } + { XD_STRUCT_PTR, offsetof(base_type, base), XD_INDIRECT(1, 0), sub_desc }, \ + { XD_INT, offsetof(base_type, cur) }, \ + { XD_INT_RESET, offsetof(base_type, max), XD_INDIRECT(1, 0) } /* Declaring the following structures as const puts them in the text (read-only) segment, which makes debugging inconvenient @@ -345,7 +374,7 @@ getprop, putprop, remprop, props, size, sizer, \ &(lrecord_##c_name##_lrecord_type_index), basic_p } \ -#define LRECORDP(a) (XTYPE ((a)) == Lisp_Type_Record) +#define LRECORDP(a) (XTYPE (a) == Lisp_Type_Record) #define XRECORD_LHEADER(a) ((struct lrecord_header *) XPNTR (a)) #define RECORD_TYPEP(x, ty) \ @@ -370,8 +399,7 @@ INLINE structtype * \ error_check_##c_name (Lisp_Object obj) \ { \ - assert (RECORD_TYPEP (obj, &lrecord_##c_name) || \ - MARKED_RECORD_P (obj)); \ + assert (RECORD_TYPEP (obj, &lrecord_##c_name)); \ return (structtype *) XPNTR (obj); \ } \ extern Lisp_Object Q##c_name##p @@ -381,7 +409,7 @@ INLINE structtype * \ error_check_##c_name (Lisp_Object obj) \ { \ - assert (XGCTYPE (obj) == type_enum); \ + assert (XTYPE (obj) == type_enum); \ return (structtype *) XPNTR (obj); \ } \ extern Lisp_Object Q##c_name##p @@ -392,8 +420,7 @@ # define XSETRECORD(var, p, c_name) do \ { \ XSETOBJ (var, Lisp_Type_Record, p); \ - assert (RECORD_TYPEP (var, &lrecord_##c_name) || \ - MARKED_RECORD_P (var)); \ + assert (RECORD_TYPEP (var, &lrecord_##c_name)); \ } while (0) #else /* not ERROR_CHECK_TYPECHECK */ @@ -412,7 +439,6 @@ #endif /* not ERROR_CHECK_TYPECHECK */ #define RECORDP(x, c_name) RECORD_TYPEP (x, &lrecord_##c_name) -#define GC_RECORDP(x, c_name) gc_record_type_p (x, &lrecord_##c_name) /* Note: we now have two different kinds of type-checking macros. The "old" kind has now been renamed CONCHECK_foo. The reason for @@ -459,9 +485,6 @@ #define alloc_lcrecord_type(type, lrecord_implementation) \ ((type *) alloc_lcrecord (sizeof (type), lrecord_implementation)) -int gc_record_type_p (Lisp_Object frob, - CONST struct lrecord_implementation *type); - /* Copy the data from one lcrecord structure into another, but don't overwrite the header information. */ diff -r 28d9c139be4c -r 11054d720c21 src/lstream.c --- a/src/lstream.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/lstream.c Mon Aug 13 11:26:11 2007 +0200 @@ -134,10 +134,10 @@ #define MAX_READ_SIZE 512 static Lisp_Object -mark_lstream (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_lstream (Lisp_Object obj) { Lstream *lstr = XLSTREAM (obj); - return lstr->imp->marker ? (lstr->imp->marker) (obj, markobj) : Qnil; + return lstr->imp->marker ? (lstr->imp->marker) (obj) : Qnil; } static void @@ -1214,7 +1214,7 @@ } static Lisp_Object -lisp_string_marker (Lisp_Object stream, void (*markobj) (Lisp_Object)) +lisp_string_marker (Lisp_Object stream) { struct lisp_string_stream *str = LISP_STRING_STREAM_DATA (XLSTREAM (stream)); return str->obj; @@ -1612,13 +1612,13 @@ } static Lisp_Object -lisp_buffer_marker (Lisp_Object stream, void (*markobj) (Lisp_Object)) +lisp_buffer_marker (Lisp_Object stream) { struct lisp_buffer_stream *str = LISP_BUFFER_STREAM_DATA (XLSTREAM (stream)); - markobj (str->start); - markobj (str->end); + mark_object (str->start); + mark_object (str->end); return str->buffer; } @@ -1673,13 +1673,19 @@ } void -vars_of_lstream (void) +reinit_vars_of_lstream (void) { int i; for (i = 0; i < countof (Vlstream_free_list); i++) { Vlstream_free_list[i] = Qnil; - staticpro (&Vlstream_free_list[i]); + staticpro_nodump (&Vlstream_free_list[i]); } } + +void +vars_of_lstream (void) +{ + reinit_vars_of_lstream (); +} diff -r 28d9c139be4c -r 11054d720c21 src/lstream.h --- a/src/lstream.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/lstream.h Mon Aug 13 11:26:11 2007 +0200 @@ -129,7 +129,7 @@ int (*closer) (Lstream *stream); /* Mark this object for garbage collection. Same semantics as a standard Lisp_Object marker. This function can be NULL. */ - Lisp_Object (*marker) (Lisp_Object lstream, void (*markfun) (Lisp_Object)); + Lisp_Object (*marker) (Lisp_Object lstream); } Lstream_implementation; #define DEFINE_LSTREAM_IMPLEMENTATION(name,c_name,size) \ diff -r 28d9c139be4c -r 11054d720c21 src/m/iris4d.h --- a/src/m/iris4d.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/m/iris4d.h Mon Aug 13 11:26:11 2007 +0200 @@ -99,8 +99,7 @@ #ifdef USG5_4 #undef UNEXEC -/* FSF renames this file to unexsgi.o */ -#define UNEXEC "unexelfsgi.o" +#define UNEXEC "unexelf.o" #else #define UNEXEC "unexmips.o" #endif diff -r 28d9c139be4c -r 11054d720c21 src/m/iris5d.h --- a/src/m/iris5d.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/m/iris5d.h Mon Aug 13 11:26:11 2007 +0200 @@ -101,8 +101,7 @@ #ifdef UNEXEC #undef UNEXEC #endif -/* FSF renames this file to unexsgi.o */ -#define UNEXEC "unexelfsgi.o" +#define UNEXEC "unexelf.o" #define TEXT_START 0x400000 diff -r 28d9c139be4c -r 11054d720c21 src/m/mips.h --- a/src/m/mips.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/m/mips.h Mon Aug 13 11:26:11 2007 +0200 @@ -63,10 +63,12 @@ #define LOAD_AVE_CVT(x) (int) (((double) (x)) * 100.0 / 256.0) +#ifndef linux /* CDC EP/IX 1.4.3 uses /unix */ #undef KERNEL_FILE #define KERNEL_FILE "/unix" +#endif /* ! linux */ /* Define CANNOT_DUMP on machines where unexec does not work. Then the function dump-emacs will not be defined @@ -106,16 +108,23 @@ /* This machine requires completely different unexec code which lives in a separate file. Specify the file name. */ +#ifndef linux #define UNEXEC "unexmips.o" - +#endif /* !linux */ /* Describe layout of the address space in an executing process. */ +#ifdef linux +#define TEXT_START 0x00400000 +#define DATA_START 0x10000000 +#define DATA_SEG_BITS 0x10000000 +#else /* !linux */ #define TEXT_START 0x400000 #define DATA_START 0x800000 +#endif /* linux */ /* Alter some of the options used when linking. */ -#ifndef NEWSOS5 +#if !defined(NEWSOS5) && !defined(linux) #ifdef BSD /* DECstations don't have this library. */ @@ -138,9 +147,9 @@ #define C_DEBUG_SWITCH "-O -g3" #endif /* not BSD */ -#endif /* not NEWSOS5 */ +#endif /* !NEWSOS5 && !linux */ -#ifndef NEWSOS5 +#if !defined(NEWSOS5) && !defined(linux) #ifdef USG /* Don't try to use SIGIO even though it is defined. */ @@ -167,4 +176,4 @@ #define TERMINFO #undef MAIL_USE_FLOCK /* Someone should check this. */ #endif /* BSD */ -#endif /* not NEWSOS5 */ +#endif /* !NEWSOS5 && !linux */ diff -r 28d9c139be4c -r 11054d720c21 src/marker.c --- a/src/marker.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/marker.c Mon Aug 13 11:26:11 2007 +0200 @@ -36,7 +36,7 @@ #include "buffer.h" static Lisp_Object -mark_marker (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_marker (Lisp_Object obj) { struct Lisp_Marker *marker = XMARKER (obj); Lisp_Object buf; @@ -66,7 +66,7 @@ write_c_string (GETTEXT ("in no buffer"), printcharfun); else { - sprintf (buf, "at %d in ", marker_position (obj)); + sprintf (buf, "at %ld in ", (long) marker_position (obj)); write_c_string (buf, printcharfun); print_internal (marker->buffer->name, printcharfun, 0); } diff -r 28d9c139be4c -r 11054d720c21 src/menubar-x.c --- a/src/menubar-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/menubar-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -675,7 +675,6 @@ if (eev) { Position shellx, shelly, framex, framey; - Widget shell = XtParent (daddy); Arg al [2]; btn->time = eev->timestamp; btn->button = eev->event.button.button; @@ -683,9 +682,16 @@ btn->subwindow = (Window) NULL; btn->x = eev->event.button.x; btn->y = eev->event.button.y; - XtSetArg (al [0], XtNx, &shellx); - XtSetArg (al [1], XtNy, &shelly); - XtGetValues (shell, al, 2); + shellx = shelly = 0; +#ifndef HAVE_WMCOMMAND + { + Widget shell = XtParent (daddy); + + XtSetArg (al [0], XtNx, &shellx); + XtSetArg (al [1], XtNy, &shelly); + XtGetValues (shell, al, 2); + } +#endif XtSetArg (al [0], XtNx, &framex); XtSetArg (al [1], XtNy, &framey); XtGetValues (daddy, al, 2); @@ -855,9 +861,15 @@ } void +reinit_vars_of_menubar_x (void) +{ + last_popup_menu_selection_callback_id = (LWLIB_ID) -1; +} + +void vars_of_menubar_x (void) { - last_popup_menu_selection_callback_id = (LWLIB_ID) -1; + reinit_vars_of_menubar_x (); #if defined (LWLIB_MENUBARS_LUCID) Fprovide (intern ("lucid-menubars")); diff -r 28d9c139be4c -r 11054d720c21 src/menubar.c --- a/src/menubar.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/menubar.c Mon Aug 13 11:26:11 2007 +0200 @@ -378,7 +378,6 @@ Fcons (Fvector (3, &menu_item[0]), Qnil)), Qnil); - Vblank_menubar = Fpurecopy (Vblank_menubar); staticpro (&Vblank_menubar); } diff -r 28d9c139be4c -r 11054d720c21 src/minibuf.c --- a/src/minibuf.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/minibuf.c Mon Aug 13 11:26:11 2007 +0200 @@ -936,9 +936,15 @@ } void +reinit_vars_of_minibuf (void) +{ + minibuf_level = 0; +} + +void vars_of_minibuf (void) { - minibuf_level = 0; + reinit_vars_of_minibuf (); staticpro (&Vminibuf_prompt); Vminibuf_prompt = Qnil; @@ -965,7 +971,7 @@ } void -complex_vars_of_minibuf (void) +reinit_complex_vars_of_minibuf (void) { /* This function can GC */ #ifdef I18N3 @@ -974,8 +980,14 @@ #endif Vminibuffer_zero = Fget_buffer_create - (Fpurecopy (build_string (DEFER_GETTEXT (" *Minibuf-0*")))); + (build_string (DEFER_GETTEXT (" *Minibuf-0*"))); Vecho_area_buffer = Fget_buffer_create - (Fpurecopy (build_string (DEFER_GETTEXT (" *Echo Area*")))); + (build_string (DEFER_GETTEXT (" *Echo Area*"))); } + +void +complex_vars_of_minibuf (void) +{ + reinit_complex_vars_of_minibuf (); +} diff -r 28d9c139be4c -r 11054d720c21 src/mule-ccl.c --- a/src/mule-ccl.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/mule-ccl.c Mon Aug 13 11:26:11 2007 +0200 @@ -760,7 +760,7 @@ int i, j, op; int stack_idx = ccl->stack_idx; /* Instruction counter of the current CCL code. */ - int this_ic; + int this_ic = 0; if (ic >= ccl->eof_ic) ic = CCL_HEADER_MAIN; @@ -1667,7 +1667,7 @@ function converts symbols of code conversion maps and character translation tables embeded in the CCL code into their ID numbers. */ -Lisp_Object +static Lisp_Object resolve_symbol_ccl_program (Lisp_Object ccl) { int i, veclen; @@ -1734,8 +1734,8 @@ int i; Lisp_Object ccl_id; - if ((SYMBOLP (ccl_prog)) && - (!NILP (ccl_id = Fget (ccl_prog, Qccl_program_idx, Qnil)))) + if (SYMBOLP (ccl_prog) && + !NILP (ccl_id = Fget (ccl_prog, Qccl_program_idx, Qnil))) { ccl_prog = XVECTOR_DATA (Vccl_program_table)[XUINT (ccl_id)]; CHECK_LIST (ccl_prog); @@ -1801,8 +1801,8 @@ struct gcpro gcpro1, gcpro2, gcpro3; Lisp_Object ccl_id; - if ((SYMBOLP (ccl_prog)) && - (!NILP (ccl_id = Fget (ccl_prog, Qccl_program_idx, Qnil)))) + if (SYMBOLP (ccl_prog) && + !NILP (ccl_id = Fget (ccl_prog, Qccl_program_idx, Qnil))) { ccl_prog = XVECTOR (Vccl_program_table)->contents[XUINT (ccl_id)]; CHECK_LIST (ccl_prog); diff -r 28d9c139be4c -r 11054d720c21 src/mule-charset.c --- a/src/mule-charset.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/mule-charset.c Mon Aug 13 11:26:11 2007 +0200 @@ -74,11 +74,17 @@ #endif /* ENABLE_COMPOSITE_CHARS */ -/* Table of charsets indexed by leading byte. */ -Lisp_Object charset_by_leading_byte[128]; +struct charset_lookup *chlook; -/* Table of charsets indexed by type/final-byte/direction. */ -Lisp_Object charset_by_attributes[4][128][2]; +static const struct lrecord_description charset_lookup_description_1[] = { + { XD_LISP_OBJECT, offsetof(struct charset_lookup, charset_by_leading_byte), 128+4*128*2 }, + { XD_END } +}; + +static const struct struct_description charset_lookup_description = { + sizeof(struct charset_lookup), + charset_lookup_description_1 +}; /* Table of number of bytes in the string representation of a character indexed by the first byte of that representation. @@ -395,15 +401,15 @@ /************************************************************************/ static Lisp_Object -mark_charset (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_charset (Lisp_Object obj) { struct Lisp_Charset *cs = XCHARSET (obj); - markobj (cs->short_name); - markobj (cs->long_name); - markobj (cs->doc_string); - markobj (cs->registry); - markobj (cs->ccl_program); + mark_object (cs->short_name); + mark_object (cs->long_name); + mark_object (cs->doc_string); + mark_object (cs->registry); + mark_object (cs->ccl_program); return cs->name; } @@ -488,12 +494,12 @@ /* some charsets do not have final characters. This includes ASCII, Control-1, Composite, and the two faux private charsets. */ - assert (NILP (charset_by_attributes[type][final][direction])); - charset_by_attributes[type][final][direction] = obj; + assert (NILP (chlook->charset_by_attributes[type][final][direction])); + chlook->charset_by_attributes[type][final][direction] = obj; } - assert (NILP (charset_by_leading_byte[id - 128])); - charset_by_leading_byte[id - 128] = obj; + assert (NILP (chlook->charset_by_leading_byte[id - 128])); + chlook->charset_by_leading_byte[id - 128] = obj; if (id < 0xA0) /* official leading byte */ rep_bytes_by_first_byte[id] = rep_bytes; @@ -1294,15 +1300,18 @@ { int i, j, k; + chlook = xnew (struct charset_lookup); + dumpstruct (&chlook, &charset_lookup_description); + /* Table of charsets indexed by leading byte. */ - for (i = 0; i < countof (charset_by_leading_byte); i++) - charset_by_leading_byte[i] = Qnil; + for (i = 0; i < countof (chlook->charset_by_leading_byte); i++) + chlook->charset_by_leading_byte[i] = Qnil; /* Table of charsets indexed by type/final-byte/direction. */ - for (i = 0; i < countof (charset_by_attributes); i++) - for (j = 0; j < countof (charset_by_attributes[0]); j++) - for (k = 0; k < countof (charset_by_attributes[0][0]); k++) - charset_by_attributes[i][j][k] = Qnil; + for (i = 0; i < countof (chlook->charset_by_attributes); i++) + for (j = 0; j < countof (chlook->charset_by_attributes[0]); j++) + for (k = 0; k < countof (chlook->charset_by_attributes[0][0]); k++) + chlook->charset_by_attributes[i][j][k] = Qnil; next_allocated_1_byte_leading_byte = MIN_LEADING_BYTE_PRIVATE_1; next_allocated_2_byte_leading_byte = MIN_LEADING_BYTE_PRIVATE_2; @@ -1318,6 +1327,7 @@ /* Predefined character sets. We store them into variables for ease of access. */ + staticpro (&Vcharset_ascii); Vcharset_ascii = make_charset (LEADING_BYTE_ASCII, Qascii, 1, CHARSET_TYPE_94, 1, 0, 'B', @@ -1326,6 +1336,7 @@ build_string ("ASCII)"), build_string ("ASCII (ISO646 IRV)"), build_string ("\\(iso8859-[0-9]*\\|-ascii\\)")); + staticpro (&Vcharset_control_1); Vcharset_control_1 = make_charset (LEADING_BYTE_CONTROL_1, Qcontrol_1, 2, CHARSET_TYPE_94, 1, 1, 0, @@ -1334,6 +1345,7 @@ build_string ("Control characters"), build_string ("Control characters 128-191"), build_string ("")); + staticpro (&Vcharset_latin_iso8859_1); Vcharset_latin_iso8859_1 = make_charset (LEADING_BYTE_LATIN_ISO8859_1, Qlatin_iso8859_1, 2, CHARSET_TYPE_96, 1, 1, 'A', @@ -1342,6 +1354,7 @@ build_string ("ISO8859-1 (Latin-1)"), build_string ("ISO8859-1 (Latin-1)"), build_string ("iso8859-1")); + staticpro (&Vcharset_latin_iso8859_2); Vcharset_latin_iso8859_2 = make_charset (LEADING_BYTE_LATIN_ISO8859_2, Qlatin_iso8859_2, 2, CHARSET_TYPE_96, 1, 1, 'B', @@ -1350,6 +1363,7 @@ build_string ("ISO8859-2 (Latin-2)"), build_string ("ISO8859-2 (Latin-2)"), build_string ("iso8859-2")); + staticpro (&Vcharset_latin_iso8859_3); Vcharset_latin_iso8859_3 = make_charset (LEADING_BYTE_LATIN_ISO8859_3, Qlatin_iso8859_3, 2, CHARSET_TYPE_96, 1, 1, 'C', @@ -1358,6 +1372,7 @@ build_string ("ISO8859-3 (Latin-3)"), build_string ("ISO8859-3 (Latin-3)"), build_string ("iso8859-3")); + staticpro (&Vcharset_latin_iso8859_4); Vcharset_latin_iso8859_4 = make_charset (LEADING_BYTE_LATIN_ISO8859_4, Qlatin_iso8859_4, 2, CHARSET_TYPE_96, 1, 1, 'D', @@ -1366,6 +1381,7 @@ build_string ("ISO8859-4 (Latin-4)"), build_string ("ISO8859-4 (Latin-4)"), build_string ("iso8859-4")); + staticpro (&Vcharset_thai_tis620); Vcharset_thai_tis620 = make_charset (LEADING_BYTE_THAI_TIS620, Qthai_tis620, 2, CHARSET_TYPE_96, 1, 1, 'T', @@ -1374,6 +1390,7 @@ build_string ("TIS620 (Thai)"), build_string ("TIS620.2529 (Thai)"), build_string ("tis620")); + staticpro (&Vcharset_greek_iso8859_7); Vcharset_greek_iso8859_7 = make_charset (LEADING_BYTE_GREEK_ISO8859_7, Qgreek_iso8859_7, 2, CHARSET_TYPE_96, 1, 1, 'F', @@ -1382,6 +1399,7 @@ build_string ("ISO8859-7 (Greek)"), build_string ("ISO8859-7 (Greek)"), build_string ("iso8859-7")); + staticpro (&Vcharset_arabic_iso8859_6); Vcharset_arabic_iso8859_6 = make_charset (LEADING_BYTE_ARABIC_ISO8859_6, Qarabic_iso8859_6, 2, CHARSET_TYPE_96, 1, 1, 'G', @@ -1390,6 +1408,7 @@ build_string ("ISO8859-6 (Arabic)"), build_string ("ISO8859-6 (Arabic)"), build_string ("iso8859-6")); + staticpro (&Vcharset_hebrew_iso8859_8); Vcharset_hebrew_iso8859_8 = make_charset (LEADING_BYTE_HEBREW_ISO8859_8, Qhebrew_iso8859_8, 2, CHARSET_TYPE_96, 1, 1, 'H', @@ -1398,6 +1417,7 @@ build_string ("ISO8859-8 (Hebrew)"), build_string ("ISO8859-8 (Hebrew)"), build_string ("iso8859-8")); + staticpro (&Vcharset_katakana_jisx0201); Vcharset_katakana_jisx0201 = make_charset (LEADING_BYTE_KATAKANA_JISX0201, Qkatakana_jisx0201, 2, CHARSET_TYPE_94, 1, 1, 'I', @@ -1406,6 +1426,7 @@ build_string ("JISX0201.1976 (Japanese Kana)"), build_string ("JISX0201.1976 Japanese Kana"), build_string ("jisx0201.1976")); + staticpro (&Vcharset_latin_jisx0201); Vcharset_latin_jisx0201 = make_charset (LEADING_BYTE_LATIN_JISX0201, Qlatin_jisx0201, 2, CHARSET_TYPE_94, 1, 0, 'J', @@ -1414,6 +1435,7 @@ build_string ("JISX0201.1976 (Japanese Roman)"), build_string ("JISX0201.1976 Japanese Roman"), build_string ("jisx0201.1976")); + staticpro (&Vcharset_cyrillic_iso8859_5); Vcharset_cyrillic_iso8859_5 = make_charset (LEADING_BYTE_CYRILLIC_ISO8859_5, Qcyrillic_iso8859_5, 2, CHARSET_TYPE_96, 1, 1, 'L', @@ -1422,6 +1444,7 @@ build_string ("ISO8859-5 (Cyrillic)"), build_string ("ISO8859-5 (Cyrillic)"), build_string ("iso8859-5")); + staticpro (&Vcharset_latin_iso8859_9); Vcharset_latin_iso8859_9 = make_charset (LEADING_BYTE_LATIN_ISO8859_9, Qlatin_iso8859_9, 2, CHARSET_TYPE_96, 1, 1, 'M', @@ -1430,6 +1453,7 @@ build_string ("ISO8859-9 (Latin-5)"), build_string ("ISO8859-9 (Latin-5)"), build_string ("iso8859-9")); + staticpro (&Vcharset_japanese_jisx0208_1978); Vcharset_japanese_jisx0208_1978 = make_charset (LEADING_BYTE_JAPANESE_JISX0208_1978, Qjapanese_jisx0208_1978, 3, CHARSET_TYPE_94X94, 2, 0, '@', @@ -1439,6 +1463,7 @@ build_string ("JISX0208.1978 Japanese Kanji (so called \"old JIS\")"), build_string ("\\(jisx0208\\|jisc6226\\)\\.1978")); + staticpro (&Vcharset_chinese_gb2312); Vcharset_chinese_gb2312 = make_charset (LEADING_BYTE_CHINESE_GB2312, Qchinese_gb2312, 3, CHARSET_TYPE_94X94, 2, 0, 'A', @@ -1447,6 +1472,7 @@ build_string ("GB2312)"), build_string ("GB2312 Chinese simplified"), build_string ("gb2312")); + staticpro (&Vcharset_japanese_jisx0208); Vcharset_japanese_jisx0208 = make_charset (LEADING_BYTE_JAPANESE_JISX0208, Qjapanese_jisx0208, 3, CHARSET_TYPE_94X94, 2, 0, 'B', @@ -1455,6 +1481,7 @@ build_string ("JISX0208.1983/1990 (Japanese)"), build_string ("JISX0208.1983/1990 Japanese Kanji"), build_string ("jisx0208.19\\(83\\|90\\)")); + staticpro (&Vcharset_korean_ksc5601); Vcharset_korean_ksc5601 = make_charset (LEADING_BYTE_KOREAN_KSC5601, Qkorean_ksc5601, 3, CHARSET_TYPE_94X94, 2, 0, 'C', @@ -1463,6 +1490,7 @@ build_string ("KSC5601 (Korean"), build_string ("KSC5601 Korean Hangul and Hanja"), build_string ("ksc5601")); + staticpro (&Vcharset_japanese_jisx0212); Vcharset_japanese_jisx0212 = make_charset (LEADING_BYTE_JAPANESE_JISX0212, Qjapanese_jisx0212, 3, CHARSET_TYPE_94X94, 2, 0, 'D', @@ -1473,6 +1501,7 @@ build_string ("jisx0212")); #define CHINESE_CNS_PLANE_RE(n) "cns11643[.-]\\(.*[.-]\\)?" n "$" + staticpro (&Vcharset_chinese_cns11643_1); Vcharset_chinese_cns11643_1 = make_charset (LEADING_BYTE_CHINESE_CNS11643_1, Qchinese_cns11643_1, 3, CHARSET_TYPE_94X94, 2, 0, 'G', @@ -1482,6 +1511,7 @@ build_string ("CNS 11643 Plane 1 Chinese traditional"), build_string (CHINESE_CNS_PLANE_RE("1"))); + staticpro (&Vcharset_chinese_cns11643_2); Vcharset_chinese_cns11643_2 = make_charset (LEADING_BYTE_CHINESE_CNS11643_2, Qchinese_cns11643_2, 3, CHARSET_TYPE_94X94, 2, 0, 'H', @@ -1491,6 +1521,7 @@ build_string ("CNS 11643 Plane 2 Chinese traditional"), build_string (CHINESE_CNS_PLANE_RE("2"))); + staticpro (&Vcharset_chinese_big5_1); Vcharset_chinese_big5_1 = make_charset (LEADING_BYTE_CHINESE_BIG5_1, Qchinese_big5_1, 3, CHARSET_TYPE_94X94, 2, 0, '0', @@ -1500,6 +1531,7 @@ build_string ("Big5 Level-1 Chinese traditional"), build_string ("big5")); + staticpro (&Vcharset_chinese_big5_2); Vcharset_chinese_big5_2 = make_charset (LEADING_BYTE_CHINESE_BIG5_2, Qchinese_big5_2, 3, CHARSET_TYPE_94X94, 2, 0, '1', @@ -1515,6 +1547,7 @@ /* #### For simplicity, we put composite chars into a 96x96 charset. This is going to lead to problems because you can run out of room, esp. as we don't yet recycle numbers. */ + staticpro (&Vcharset_composite); Vcharset_composite = make_charset (LEADING_BYTE_COMPOSITE, Qcomposite, 3, CHARSET_TYPE_96X96, 2, 0, 0, @@ -1524,6 +1557,7 @@ build_string ("Composite characters"), build_string ("")); + /* #### not dumped properly */ composite_char_row_next = 32; composite_char_col_next = 32; diff -r 28d9c139be4c -r 11054d720c21 src/mule-charset.h --- a/src/mule-charset.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/mule-charset.h Mon Aug 13 11:26:11 2007 +0200 @@ -486,7 +486,6 @@ #define XCHARSET(x) XRECORD (x, charset, struct Lisp_Charset) #define XSETCHARSET(x, p) XSETRECORD (x, p, charset) #define CHARSETP(x) RECORDP (x, charset) -#define GC_CHARSETP(x) GC_RECORDP (x, charset) #define CHECK_CHARSET(x) CHECK_RECORD (x, charset) #define CONCHECK_CHARSET(x) CONCHECK_RECORD (x, charset) @@ -500,7 +499,7 @@ /* Leading byte and id have been regrouped. -- OG */ #define CHARSET_ID(cs) ((cs)->id) -#define CHARSET_LEADING_BYTE(cs) ((Bufbyte)(CHARSET_ID(cs))) +#define CHARSET_LEADING_BYTE(cs) ((Bufbyte) CHARSET_ID(cs)) #define CHARSET_NAME(cs) ((cs)->name) #define CHARSET_SHORT_NAME(cs) ((cs)->short_name) #define CHARSET_LONG_NAME(cs) ((cs)->long_name) @@ -540,11 +539,15 @@ #define XCHARSET_REVERSE_DIRECTION_CHARSET(cs) \ CHARSET_REVERSE_DIRECTION_CHARSET (XCHARSET (cs)) -/* Table of charsets indexed by (leading byte - 128). */ -extern Lisp_Object charset_by_leading_byte[128]; +struct charset_lookup { + /* Table of charsets indexed by leading byte. */ + Lisp_Object charset_by_leading_byte[128]; + + /* Table of charsets indexed by type/final-byte/direction. */ + Lisp_Object charset_by_attributes[4][128][2]; +}; -/* Table of charsets indexed by type/final-byte/direction. */ -extern Lisp_Object charset_by_attributes[4][128][2]; +extern struct charset_lookup *chlook; /* Table of number of bytes in the string representation of a character indexed by the first byte of that representation. @@ -566,17 +569,17 @@ CHARSET_BY_LEADING_BYTE (int lb) { assert (lb >= 0x80 && lb <= 0xFF); - return charset_by_leading_byte[lb - 128]; + return chlook->charset_by_leading_byte[lb - 128]; } #else -#define CHARSET_BY_LEADING_BYTE(lb) (charset_by_leading_byte[(lb) - 128]) +#define CHARSET_BY_LEADING_BYTE(lb) (chlook->charset_by_leading_byte[(lb) - 128]) #endif #define CHARSET_BY_ATTRIBUTES(type, final, dir) \ - (charset_by_attributes[type][final][dir]) + (chlook->charset_by_attributes[type][final][dir]) #ifdef ERROR_CHECK_TYPECHECK diff -r 28d9c139be4c -r 11054d720c21 src/mule-wnnfns.c --- a/src/mule-wnnfns.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/mule-wnnfns.c Mon Aug 13 11:26:11 2007 +0200 @@ -1875,9 +1875,22 @@ } void +reinit_vars_of_mule_wnn (void) +{ + int i; + + for (i = 0; i < NSERVER; i++) + { + wnnfns_buf[i] = (struct wnn_buf *) 0; + wnnfns_env_norm[i] = (struct wnn_env *) 0; + wnnfns_env_rev[i] = (struct wnn_env *) 0; + } +} + +void vars_of_mule_wnn (void) { - int i; + reinit_vars_of_mule_wnn (); DEFVAR_INT ("lb-sisheng", &lb_sisheng /* Leading character for Sisheng. @@ -1901,13 +1914,6 @@ Vwnn_uniq_level = Qwnn_uniq; - for (i = 0; i < NSERVER; i++) - { - wnnfns_buf[i] = (struct wnn_buf *) 0; - wnnfns_env_norm[i] = (struct wnn_env *) 0; - wnnfns_env_rev[i] = (struct wnn_env *) 0; - } - Fprovide(intern("wnn")); } diff -r 28d9c139be4c -r 11054d720c21 src/ntheap.h --- a/src/ntheap.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/ntheap.h Mon Aug 13 11:26:11 2007 +0200 @@ -87,7 +87,7 @@ /* Useful routines for manipulating memory-mapped files. */ typedef struct file_data { - char *name; + CONST char *name; unsigned long size; HANDLE file; HANDLE file_mapping; diff -r 28d9c139be4c -r 11054d720c21 src/ntproc.c --- a/src/ntproc.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/ntproc.c Mon Aug 13 11:26:11 2007 +0200 @@ -1456,8 +1456,8 @@ void vars_of_ntproc (void) { - Qhigh = intern ("high"); - Qlow = intern ("low"); + defsymbol (&Qhigh, "high"); + defsymbol (&Qlow, "low"); DEFVAR_LISP ("win32-quote-process-args", &Vwin32_quote_process_args /* Non-nil enables quoting of process arguments to ensure correct parsing. diff -r 28d9c139be4c -r 11054d720c21 src/objects-msw.c --- a/src/objects-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/objects-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -1066,8 +1066,7 @@ #if 0 static void -mswindows_mark_color_instance (struct Lisp_Color_Instance *c, - void (*markobj) (Lisp_Object)) +mswindows_mark_color_instance (struct Lisp_Color_Instance *c) { } #endif @@ -1105,7 +1104,7 @@ static unsigned long mswindows_color_instance_hash (struct Lisp_Color_Instance *c, int depth) { - return (unsigned long)(COLOR_INSTANCE_MSWINDOWS_COLOR(c)); + return (unsigned long) COLOR_INSTANCE_MSWINDOWS_COLOR(c); } static Lisp_Object @@ -1406,8 +1405,7 @@ #if 0 static void -mswindows_mark_font_instance (struct Lisp_Font_Instance *f, - void (*markobj) (Lisp_Object)) +mswindows_mark_font_instance (struct Lisp_Font_Instance *f) { } #endif diff -r 28d9c139be4c -r 11054d720c21 src/objects-tty.c --- a/src/objects-tty.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/objects-tty.c Mon Aug 13 11:26:11 2007 +0200 @@ -168,10 +168,9 @@ } static void -tty_mark_color_instance (struct Lisp_Color_Instance *c, - void (*markobj) (Lisp_Object)) +tty_mark_color_instance (struct Lisp_Color_Instance *c) { - markobj (COLOR_INSTANCE_TTY_SYMBOL (c)); + mark_object (COLOR_INSTANCE_TTY_SYMBOL (c)); } static void @@ -256,10 +255,9 @@ } static void -tty_mark_font_instance (struct Lisp_Font_Instance *f, - void (*markobj) (Lisp_Object)) +tty_mark_font_instance (struct Lisp_Font_Instance *f) { - markobj (FONT_INSTANCE_TTY_CHARSET (f)); + mark_object (FONT_INSTANCE_TTY_CHARSET (f)); } static void diff -r 28d9c139be4c -r 11054d720c21 src/objects-x.c --- a/src/objects-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/objects-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -28,6 +28,7 @@ #include #include "lisp.h" +#include #include "console-x.h" #include "objects-x.h" @@ -45,11 +46,13 @@ /* Replacement for XAllocColor() that tries to return the nearest available color if the colormap is full. Original was from FSFmacs, - but rewritten by Jareth Hein 97/11/25 */ + but rewritten by Jareth Hein 97/11/25 + Modified by Lee Kindness 31/08/99 to handle previous + total failure which was due to a read/write colorcell being the nearest + match - tries the next nearest... -/* Return value is 1 for normal success, 2 for nearest color success, - 3 for Non-deallocable sucess, and 0 for absolute failure (shouldn't - happen?) */ + Return value is 1 for normal success, 2 for nearest color success, + 3 for Non-deallocable sucess. */ int allocate_nearest_color (Display *display, Colormap colormap, Visual *visual, XColor *color_def) @@ -140,30 +143,35 @@ } else { + XColor *cells = NULL; + /* JH: I can't believe there's no way to go backwards from a + colormap ID and get its visual and number of entries, but X + apparently isn't built that way... */ + int no_cells = visual->map_entries; + status = 0; + if (XAllocColor (display, colormap, color_def) != 0) status = 1; - else + else while( status != 2 ) { /* If we got to this point, the colormap is full, so we're going to try and get the next closest color. The algorithm used is a least-squares matching, which is what X uses for closest color matching with StaticColor visuals. */ - XColor *cells; - /* JH: I can't believe there's no way to go backwards from a - colormap ID and get its visual and number of entries, but X - apparently isn't built that way... */ - int no_cells = visual->map_entries; int nearest; long nearest_delta, trial_delta; int x; - cells = alloca_array (XColor, no_cells); + if( cells == NULL ) + { + cells = alloca_array (XColor, no_cells); + for (x = 0; x < no_cells; x++) + cells[x].pixel = x; - for (x = 0; x < no_cells; x++) - cells[x].pixel = x; + /* read the current colormap */ + XQueryColors (display, colormap, cells, no_cells); + } - /* read the current colormap */ - XQueryColors (display, colormap, cells, no_cells); nearest = 0; /* I'm assuming CSE so I'm not going to condense this. */ nearest_delta = ((((color_def->red >> 8) - (cells[0].red >> 8)) @@ -184,7 +192,10 @@ + (((color_def->blue >> 8) - (cells[x].blue >> 8)) * ((color_def->blue >> 8) - (cells[x].blue >> 8)))); - if (trial_delta < nearest_delta) + + /* less? Ignore cells marked as previously failing */ + if( (trial_delta < nearest_delta) && + (cells[x].pixel != ULONG_MAX) ) { nearest = x; nearest_delta = trial_delta; @@ -193,12 +204,15 @@ color_def->red = cells[nearest].red; color_def->green = cells[nearest].green; color_def->blue = cells[nearest].blue; - if (XAllocColor (display, colormap, color_def) != 0) { - status = 2; - } else { - status = 0; /* JH: how does this happen??? DOES this happen??? */ - fprintf(stderr,"allocate_nearest_color returned 0!!!\n"); - } + if (XAllocColor (display, colormap, color_def) != 0) + status = 2; + else + /* LSK: Either the colour map has changed since + * we read it, or the colour is allocated + * read/write... Mark this cmap entry so it's + * ignored in the next iteration. + */ + cells[nearest].pixel = ULONG_MAX; } } return status; @@ -208,15 +222,11 @@ x_parse_nearest_color (struct device *d, XColor *color, Bufbyte *name, Bytecount len, Error_behavior errb) { - Display *dpy; - Colormap cmap; - Visual *visual; + Display *dpy = DEVICE_X_DISPLAY (d); + Colormap cmap = DEVICE_X_COLORMAP (d); + Visual *visual = DEVICE_X_VISUAL (d); int result; - dpy = DEVICE_X_DISPLAY (d); - cmap = DEVICE_X_COLORMAP(d); - visual = DEVICE_X_VISUAL (d); - xzero (*color); { CONST Extbyte *extname; @@ -447,10 +457,9 @@ } static void -x_mark_font_instance (struct Lisp_Font_Instance *f, - void (*markobj) (Lisp_Object)) +x_mark_font_instance (struct Lisp_Font_Instance *f) { - markobj (FONT_INSTANCE_X_TRUENAME (f)); + mark_object (FONT_INSTANCE_X_TRUENAME (f)); } static void diff -r 28d9c139be4c -r 11054d720c21 src/objects.c --- a/src/objects.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/objects.c Mon Aug 13 11:26:11 2007 +0200 @@ -57,12 +57,12 @@ Lisp_Object Qcolor_instancep; static Lisp_Object -mark_color_instance (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_color_instance (Lisp_Object obj) { struct Lisp_Color_Instance *c = XCOLOR_INSTANCE (obj); - markobj (c->name); + mark_object (c->name); if (!NILP (c->device)) /* Vthe_null_color_instance */ - MAYBE_DEVMETH (XDEVICE (c->device), mark_color_instance, (c, markobj)); + MAYBE_DEVMETH (XDEVICE (c->device), mark_color_instance, (c)); return c->device; } @@ -106,7 +106,7 @@ struct Lisp_Color_Instance *c2 = XCOLOR_INSTANCE (obj2); return (c1 == c2) || - ((EQ (c1->device, c2->device)) && + (EQ (c1->device, c2->device) && DEVICEP (c1->device) && HAS_DEVMETH_P (XDEVICE (c1->device), color_instance_equal) && DEVMETH (XDEVICE (c1->device), color_instance_equal, (c1, c2, depth))); @@ -237,13 +237,13 @@ Error_behavior errb); static Lisp_Object -mark_font_instance (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_font_instance (Lisp_Object obj) { struct Lisp_Font_Instance *f = XFONT_INSTANCE (obj); - markobj (f->name); + mark_object (f->name); if (!NILP (f->device)) /* Vthe_null_font_instance */ - MAYBE_DEVMETH (XDEVICE (f->device), mark_font_instance, (f, markobj)); + MAYBE_DEVMETH (XDEVICE (f->device), mark_font_instance, (f)); return f->device; } @@ -489,12 +489,12 @@ } static void -color_mark (Lisp_Object obj, void (*markobj) (Lisp_Object)) +color_mark (Lisp_Object obj) { struct Lisp_Specifier *color = XCOLOR_SPECIFIER (obj); - markobj (COLOR_SPECIFIER_FACE (color)); - markobj (COLOR_SPECIFIER_FACE_PROPERTY (color)); + mark_object (COLOR_SPECIFIER_FACE (color)); + mark_object (COLOR_SPECIFIER_FACE_PROPERTY (color)); } /* No equal or hash methods; ignore the face the color is based off @@ -667,12 +667,12 @@ } static void -font_mark (Lisp_Object obj, void (*markobj) (Lisp_Object)) +font_mark (Lisp_Object obj) { struct Lisp_Specifier *font = XFONT_SPECIFIER (obj); - markobj (FONT_SPECIFIER_FACE (font)); - markobj (FONT_SPECIFIER_FACE_PROPERTY (font)); + mark_object (FONT_SPECIFIER_FACE (font)); + mark_object (FONT_SPECIFIER_FACE_PROPERTY (font)); } /* No equal or hash methods; ignore the face the font is based off @@ -874,12 +874,12 @@ } static void -face_boolean_mark (Lisp_Object obj, void (*markobj) (Lisp_Object)) +face_boolean_mark (Lisp_Object obj) { struct Lisp_Specifier *face_boolean = XFACE_BOOLEAN_SPECIFIER (obj); - markobj (FACE_BOOLEAN_SPECIFIER_FACE (face_boolean)); - markobj (FACE_BOOLEAN_SPECIFIER_FACE_PROPERTY (face_boolean)); + mark_object (FACE_BOOLEAN_SPECIFIER_FACE (face_boolean)); + mark_object (FACE_BOOLEAN_SPECIFIER_FACE_PROPERTY (face_boolean)); } /* No equal or hash methods; ignore the face the face-boolean is based off @@ -1036,6 +1036,21 @@ defsymbol (&Qface_boolean, "face-boolean"); } +static const struct lrecord_description color_specifier_description[] = { + { XD_LISP_OBJECT, specifier_data_offset + offsetof(struct color_specifier, face), 2 }, + { XD_END } +}; + +static const struct lrecord_description font_specifier_description[] = { + { XD_LISP_OBJECT, specifier_data_offset + offsetof(struct font_specifier, face), 2 }, + { XD_END } +}; + +static const struct lrecord_description face_boolean_specifier_description[] = { + { XD_LISP_OBJECT, specifier_data_offset + offsetof(struct face_boolean_specifier, face), 2 }, + { XD_END } +}; + void specifier_type_create_objects (void) { @@ -1070,9 +1085,17 @@ } void -vars_of_objects (void) +reinit_specifier_type_create_objects (void) { - staticpro (&Vthe_null_color_instance); + REINITIALIZE_SPECIFIER_TYPE (color); + REINITIALIZE_SPECIFIER_TYPE (font); + REINITIALIZE_SPECIFIER_TYPE (face_boolean); +} + +void +reinit_vars_of_objects (void) +{ + staticpro_nodump (&Vthe_null_color_instance); { struct Lisp_Color_Instance *c = alloc_lcrecord_type (struct Lisp_Color_Instance, &lrecord_color_instance); @@ -1083,7 +1106,7 @@ XSETCOLOR_INSTANCE (Vthe_null_color_instance, c); } - staticpro (&Vthe_null_font_instance); + staticpro_nodump (&Vthe_null_font_instance); { struct Lisp_Font_Instance *f = alloc_lcrecord_type (struct Lisp_Font_Instance, &lrecord_font_instance); @@ -1099,3 +1122,9 @@ XSETFONT_INSTANCE (Vthe_null_font_instance, f); } } + +void +vars_of_objects (void) +{ + reinit_vars_of_objects (); +} diff -r 28d9c139be4c -r 11054d720c21 src/objects.h --- a/src/objects.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/objects.h Mon Aug 13 11:26:11 2007 +0200 @@ -38,7 +38,7 @@ Lisp_Object face_property; /* property of that face */ }; -#define COLOR_SPECIFIER_DATA(g) (SPECIFIER_TYPE_DATA (g, color)) +#define COLOR_SPECIFIER_DATA(g) SPECIFIER_TYPE_DATA (g, color) #define COLOR_SPECIFIER_FACE(g) (COLOR_SPECIFIER_DATA (g)->face) #define COLOR_SPECIFIER_FACE_PROPERTY(g) \ (COLOR_SPECIFIER_DATA (g)->face_property) @@ -63,7 +63,7 @@ Lisp_Object face_property; /* property of that face */ }; -#define FONT_SPECIFIER_DATA(g) (SPECIFIER_TYPE_DATA (g, font)) +#define FONT_SPECIFIER_DATA(g) SPECIFIER_TYPE_DATA (g, font) #define FONT_SPECIFIER_FACE(g) (FONT_SPECIFIER_DATA (g)->face) #define FONT_SPECIFIER_FACE_PROPERTY(g) \ (FONT_SPECIFIER_DATA (g)->face_property) @@ -88,7 +88,7 @@ Lisp_Object face_property; /* property of that face */ }; -#define FACE_BOOLEAN_SPECIFIER_DATA(g) (SPECIFIER_TYPE_DATA (g, face_boolean)) +#define FACE_BOOLEAN_SPECIFIER_DATA(g) SPECIFIER_TYPE_DATA (g, face_boolean) #define FACE_BOOLEAN_SPECIFIER_FACE(g) (FACE_BOOLEAN_SPECIFIER_DATA (g)->face) #define FACE_BOOLEAN_SPECIFIER_FACE_PROPERTY(g) \ (FACE_BOOLEAN_SPECIFIER_DATA (g)->face_property) @@ -116,7 +116,6 @@ XRECORD (x, color_instance, struct Lisp_Color_Instance) #define XSETCOLOR_INSTANCE(x, p) XSETRECORD (x, p, color_instance) #define COLOR_INSTANCEP(x) RECORDP (x, color_instance) -#define GC_COLOR_INSTANCEP(x) GC_RECORDP (x, color_instance) #define CHECK_COLOR_INSTANCE(x) CHECK_RECORD (x, color_instance) #define CONCHECK_COLOR_INSTANCE(x) CONCHECK_RECORD (x, color_instance) @@ -145,7 +144,6 @@ #define XFONT_INSTANCE(x) XRECORD (x, font_instance, struct Lisp_Font_Instance) #define XSETFONT_INSTANCE(x, p) XSETRECORD (x, p, font_instance) #define FONT_INSTANCEP(x) RECORDP (x, font_instance) -#define GC_FONT_INSTANCEP(x) GC_RECORDP (x, font_instance) #define CHECK_FONT_INSTANCE(x) CHECK_RECORD (x, font_instance) #define CONCHECK_FONT_INSTANCE(x) CONCHECK_RECORD (x, font_instance) diff -r 28d9c139be4c -r 11054d720c21 src/opaque.c --- a/src/opaque.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/opaque.c Mon Aug 13 11:26:11 2007 +0200 @@ -32,67 +32,23 @@ OPAQUE OBJECTS SHOULD NEVER ESCAPE TO THE LISP LEVEL. Some code depends on this. As such, opaque objects are a generalization of the Qunbound marker. - - "Opaque lists" are used to keep track of lots of opaque objects - of a particular size so that they can be efficiently "freed" and - re-used again without actually entering the Lisp allocation system - (and consequently doing a malloc()). */ #include #include "lisp.h" #include "opaque.h" -Lisp_Object Qopaquep; - -static int in_opaque_list_marking; - -/* Holds freed opaque objects created with make_opaque_ptr(). - We do this quite often so it's a noticeable win if we don't - create GC junk. */ Lisp_Object Vopaque_ptr_free_list; -static Lisp_Object -mark_opaque (Lisp_Object obj, void (*markobj) (Lisp_Object)) -{ - Lisp_Opaque *p = XOPAQUE (obj); - /* Egcs 1.1.1 sometimes crashes on INTP (p->size_or_chain) */ - Lisp_Object size_or_chain = p->size_or_chain; -#ifdef ERROR_CHECK_GC - if (!in_opaque_list_marking) - /* size is non-int for objects on an opaque free list. We sure - as hell better not be marking any of these objects unless - we're marking an opaque list. */ - assert (GC_INTP (size_or_chain)); - else - /* marking an opaque on the free list doesn't do any recursive - markings, so we better not have non-freed opaques on a free - list. */ - assert (!GC_INTP (size_or_chain)); -#endif - if (GC_INTP (size_or_chain) && OPAQUE_MARKFUN (p)) - return OPAQUE_MARKFUN (p) (obj, markobj); - else - return size_or_chain; -} - /* Should never, ever be called. (except by an external debugger) */ static void print_opaque (Lisp_Object obj, Lisp_Object printcharfun, int escapeflag) { CONST Lisp_Opaque *p = XOPAQUE (obj); - /* Egcs 1.1.1 sometimes crashes on INTP (p->size_or_chain) */ - Lisp_Object size_or_chain = p->size_or_chain; char buf[200]; - char size_buf[50]; - if (INTP (size_or_chain)) - sprintf (size_buf, "size=%lu", (unsigned long) OPAQUE_SIZE (p)); - else - sprintf (size_buf, "freed"); - - sprintf (buf, "#", - size_buf, (unsigned long) p); + sprintf (buf, "#", + (long)(p->size), (unsigned long) p); write_c_string (buf, printcharfun); } @@ -100,10 +56,7 @@ sizeof_opaque (CONST void *header) { CONST Lisp_Opaque *p = (CONST Lisp_Opaque *) header; - /* Egcs 1.1.1 sometimes crashes on INTP (p->size_or_chain) */ - Lisp_Object size_or_chain = p->size_or_chain; - return offsetof (Lisp_Opaque, data) - + (GC_INTP (size_or_chain) ? XINT (size_or_chain) : 0); + return offsetof (Lisp_Opaque, data) + p->size; } /* Return an opaque object of size SIZE. @@ -115,8 +68,7 @@ { Lisp_Opaque *p = (Lisp_Opaque *) alloc_lcrecord (offsetof (Lisp_Opaque, data) + size, &lrecord_opaque); - p->markfun = 0; - p->size_or_chain = make_int (size); + p->size = size; if (data == OPAQUE_CLEAR) memset (p->data, '\0', size); @@ -137,21 +89,9 @@ static int equal_opaque (Lisp_Object obj1, Lisp_Object obj2, int depth) { -#ifdef DEBUG_XEMACS - { - /* Egcs 1.1.1 sometimes crashes on INTP (p->size_or_chain) */ - Lisp_Object size_or_chain_1 = XOPAQUE (obj1)->size_or_chain; - Lisp_Object size_or_chain_2 = XOPAQUE (obj2)->size_or_chain; - assert (INTP (size_or_chain_1)); - assert (INTP (size_or_chain_2)); - assert (!XOPAQUE_MARKFUN (obj1) && !XOPAQUE_MARKFUN (obj2)); - } -#endif - { - size_t size; - return ((size = XOPAQUE_SIZE (obj1)) == XOPAQUE_SIZE (obj2) && - !memcmp (XOPAQUE_DATA (obj1), XOPAQUE_DATA (obj2), size)); - } + size_t size; + return ((size = XOPAQUE_SIZE (obj1)) == XOPAQUE_SIZE (obj2) && + !memcmp (XOPAQUE_DATA (obj1), XOPAQUE_DATA (obj2), size)); } /* This will not work correctly for opaques with subobjects! */ @@ -159,102 +99,59 @@ static unsigned long hash_opaque (Lisp_Object obj, int depth) { -#ifdef DEBUG_XEMACS - { - /* Egcs 1.1.1 sometimes crashes on INTP (p->size_or_chain) */ - Lisp_Object size_or_chain = XOPAQUE (obj)->size_or_chain; - assert (INTP (size_or_chain)); - assert (!XOPAQUE_MARKFUN (obj)); - } -#endif if (XOPAQUE_SIZE (obj) == sizeof (unsigned long)) return *((unsigned long *) XOPAQUE_DATA (obj)); else return memory_hash (XOPAQUE_DATA (obj), XOPAQUE_SIZE (obj)); } -DEFINE_LRECORD_SEQUENCE_IMPLEMENTATION ("opaque", opaque, - mark_opaque, print_opaque, 0, - equal_opaque, hash_opaque, 0, - sizeof_opaque, Lisp_Opaque); - -static Lisp_Object -mark_opaque_list (Lisp_Object obj, void (*markobj) (Lisp_Object)) -{ - in_opaque_list_marking++; - markobj (XOPAQUE_LIST (obj)->free); - in_opaque_list_marking--; - return Qnil; -} - -Lisp_Object -make_opaque_list (size_t size, - Lisp_Object (*markfun) (Lisp_Object obj, - void (*markobj) (Lisp_Object))) -{ - Lisp_Object val; - Lisp_Opaque_List *p = - alloc_lcrecord_type (Lisp_Opaque_List, &lrecord_opaque_list); - - p->markfun = markfun; - p->size = size; - p->free = Qnil; - XSETOPAQUE_LIST (val, p); - return val; -} - -DEFINE_LRECORD_IMPLEMENTATION ("opaque-list", opaque_list, - mark_opaque_list, internal_object_printer, - 0, 0, 0, 0, Lisp_Opaque_List); +static const struct lrecord_description opaque_description[] = { + { XD_END } +}; -Lisp_Object -allocate_managed_opaque (Lisp_Object opaque_list, CONST void *data) -{ - Lisp_Opaque_List *li = XOPAQUE_LIST (opaque_list); - Lisp_Object val; - - if (!NILP (li->free)) - { - val = li->free; - li->free = XOPAQUE (val)->size_or_chain; -#ifdef ERROR_CHECK_GC - assert (NILP (li->free) || OPAQUEP (li->free)); -#endif - XOPAQUE (val)->size_or_chain = make_int (li->size); - if (data) - memcpy (XOPAQUE (val)->data, data, li->size); - else - memset (XOPAQUE (val)->data, 0, li->size); - } - else - val = make_opaque (li->size, data); - XOPAQUE (val)->markfun = li->markfun; - return val; -} - -void -free_managed_opaque (Lisp_Object opaque_list, Lisp_Object opaque) -{ - Lisp_Opaque_List *li = XOPAQUE_LIST (opaque_list); - -#ifdef ERROR_CHECK_GC - { - /* Egcs 1.1.1 sometimes crashes on INTP (p->size_or_chain) */ - Lisp_Object size_or_chain = XOPAQUE (opaque)->size_or_chain; - assert (INTP (size_or_chain)); - } -#endif - XOPAQUE (opaque)->size_or_chain = li->free; - li->free = opaque; -} +DEFINE_LRECORD_SEQUENCE_IMPLEMENTATION ("opaque", opaque, + 0, print_opaque, 0, + equal_opaque, hash_opaque, + opaque_description, + sizeof_opaque, Lisp_Opaque); /* stuff to handle opaque pointers */ -Lisp_Object -make_opaque_ptr (CONST void *val) +/* Should never, ever be called. (except by an external debugger) */ +static void +print_opaque_ptr (Lisp_Object obj, Lisp_Object printcharfun, int escapeflag) +{ + CONST Lisp_Opaque_Ptr *p = XOPAQUE_PTR (obj); + char buf[200]; + + sprintf (buf, "#", + (long)(p->ptr), (unsigned long) p); + write_c_string (buf, printcharfun); +} + +static int +equal_opaque_ptr (Lisp_Object obj1, Lisp_Object obj2, int depth) { - return allocate_managed_opaque (Vopaque_ptr_free_list, - (CONST void *) &val); + return (XOPAQUE_PTR (obj1)->ptr == XOPAQUE_PTR (obj2)->ptr); +} + +static unsigned long +hash_opaque_ptr (Lisp_Object obj, int depth) +{ + return (unsigned long) XOPAQUE_PTR (obj)->ptr; +} + +DEFINE_LRECORD_IMPLEMENTATION ("opaque_ptr", opaque_ptr, + 0, print_opaque_ptr, 0, + equal_opaque_ptr, hash_opaque_ptr, 0, + Lisp_Opaque_Ptr); + +Lisp_Object +make_opaque_ptr (void *val) +{ + Lisp_Object res = allocate_managed_lcrecord(Vopaque_ptr_free_list); + set_opaque_ptr (res, val); + return res; } /* Be very very careful with this. Same admonitions as with @@ -263,18 +160,18 @@ void free_opaque_ptr (Lisp_Object ptr) { - free_managed_opaque (Vopaque_ptr_free_list, ptr); + free_managed_lcrecord (Vopaque_ptr_free_list, ptr); } -Lisp_Object -make_opaque_long (long val) +void +reinit_opaque_once_early (void) { - return make_opaque (sizeof (val), (void *) &val); + Vopaque_ptr_free_list = make_lcrecord_list (sizeof (Lisp_Opaque_Ptr), &lrecord_opaque_ptr); + staticpro_nodump (&Vopaque_ptr_free_list); } void init_opaque_once_early (void) { - Vopaque_ptr_free_list = make_opaque_list (sizeof (void *), 0); - staticpro (&Vopaque_ptr_free_list); + reinit_opaque_once_early (); } diff -r 28d9c139be4c -r 11054d720c21 src/opaque.h --- a/src/opaque.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/opaque.h Mon Aug 13 11:26:11 2007 +0200 @@ -35,69 +35,46 @@ typedef struct Lisp_Opaque { struct lcrecord_header header; - Lisp_Object (*markfun) (Lisp_Object obj, void (*markobj) (Lisp_Object)); - /* An integral size for non-freed objects, an opaque or nil for - freed objects. */ - Lisp_Object size_or_chain; + size_t size; max_align_t data[1]; } Lisp_Opaque; -typedef struct Lisp_Opaque_List -{ - struct lcrecord_header header; - /* `markfun' allows you to put lisp objects inside of opaque objects - without having to create a new object type. */ - Lisp_Object (*markfun) (Lisp_Object obj, void (*markobj) (Lisp_Object)); - Lisp_Object free; - size_t size; -} Lisp_Opaque_List; - DECLARE_LRECORD (opaque, Lisp_Opaque); #define XOPAQUE(x) XRECORD (x, opaque, Lisp_Opaque) #define XSETOPAQUE(x, p) XSETRECORD (x, p, opaque) #define OPAQUEP(x) RECORDP (x, opaque) -#define GC_OPAQUEP(x) GC_RECORDP (x, opaque) /* #define CHECK_OPAQUE(x) CHECK_RECORD (x, opaque) Opaque pointers should never escape to the Lisp level, so functions should not be doing this. */ -DECLARE_LRECORD (opaque_list, Lisp_Opaque_List); -#define XOPAQUE_LIST(x) XRECORD (x, opaque_list, Lisp_Opaque_List) -#define XSETOPAQUE_LIST(x, p) XSETRECORD (x, p, opaque_list) -#define OPAQUE_LISTP(x) RECORDP (x, opaque_list) -#define GC_OPAQUE_LISTP(x) GC_RECORDP (x, opaque_list) -/* #define CHECK_OPAQUE_LIST(x) CHECK_RECORD (x, opaque_list) - Opaque lists should never escape to the Lisp level, so - functions should not be doing this. */ - /* Alternative DATA arguments to make_opaque */ #define OPAQUE_CLEAR ((CONST void *) 0) #define OPAQUE_UNINIT ((CONST void *) -1) -Lisp_Object make_opaque (size_t size, CONST void *data); -Lisp_Object make_opaque_ptr (CONST void *val); -Lisp_Object make_opaque_long (long val); -void free_opaque_ptr (Lisp_Object ptr); - -#define OPAQUE_SIZE(op) XINT ((op)->size_or_chain) +#define OPAQUE_SIZE(op) ((op)->size) #define OPAQUE_DATA(op) ((void *) ((op)->data)) #define OPAQUE_MARKFUN(op) ((op)->markfun) #define XOPAQUE_SIZE(op) OPAQUE_SIZE (XOPAQUE (op)) #define XOPAQUE_DATA(op) OPAQUE_DATA (XOPAQUE (op)) #define XOPAQUE_MARKFUN(op) OPAQUE_MARKFUN (XOPAQUE (op)) -#define get_opaque_ptr(op) (* (void **) XOPAQUE_DATA (op)) -#define set_opaque_ptr(op, ptr) (get_opaque_ptr (op) = (void *) ptr) -#define get_opaque_long(op) (* (long *) XOPAQUE_DATA (op)) -#define set_opaque_long(op, ptr) (get_opaque_long (op) = ptr) -#define set_opaque_markfun(op, fun) (XOPAQUE_MARKFUN (op) = fun) +Lisp_Object make_opaque (size_t size, CONST void *data); + +typedef struct Lisp_Opaque_Ptr +{ + struct lcrecord_header header; + void *ptr; +} Lisp_Opaque_Ptr; -Lisp_Object make_opaque_list (size_t size, - Lisp_Object (*markfun) - (Lisp_Object obj, - void (*markobj) (Lisp_Object))); -Lisp_Object allocate_managed_opaque (Lisp_Object opaque_list, - CONST void *data); -void free_managed_opaque (Lisp_Object opaque_list, Lisp_Object opaque); +DECLARE_LRECORD (opaque_ptr, Lisp_Opaque_Ptr); +#define XOPAQUE_PTR(x) XRECORD (x, opaque_ptr, Lisp_Opaque_Ptr) +#define XSETOPAQUE_PTR(x, p) XSETRECORD (x, p, opaque_ptr) +#define OPAQUE_PTRP(x) RECORDP (x, opaque_ptr) + +Lisp_Object make_opaque_ptr (void *val); +void free_opaque_ptr (Lisp_Object ptr); + +#define get_opaque_ptr(op) (XOPAQUE_PTR (op)->ptr) +#define set_opaque_ptr(op, ptr_) (XOPAQUE_PTR (op)->ptr = (ptr_)) #endif /* _XEMACS_OPAQUE_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/print.c --- a/src/print.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/print.c Mon Aug 13 11:26:11 2007 +0200 @@ -51,14 +51,13 @@ /* The subroutine object for external-debugging-output is kept here for the convenience of the debugger. */ Lisp_Object Qexternal_debugging_output; -Lisp_Object Qalternate_debugging_output; /* Avoid actual stack overflow in print. */ static int print_depth; /* Detect most circularities to print finite output. */ #define PRINT_CIRCLE 200 -Lisp_Object being_printed[PRINT_CIRCLE]; +static Lisp_Object being_printed[PRINT_CIRCLE]; /* Maximum length of list or vector to print in full; noninteger means effectively infinity */ @@ -92,9 +91,6 @@ Lisp_Object Vprint_gensym; Lisp_Object Vprint_gensym_alist; -Lisp_Object Qprint_escape_newlines; -Lisp_Object Qprint_readably; - Lisp_Object Qdisplay_error; Lisp_Object Qprint_message_label; @@ -711,7 +707,6 @@ #ifdef LISP_FLOAT_TYPE Lisp_Object Vfloat_output_format; -Lisp_Object Qfloat_output_format; /* * This buffer should be at least as large as the max string size of the @@ -1362,8 +1357,8 @@ getting rid of this function altogether? Does anything actually *use* it? --hniksic */ -int alternate_do_pointer; -char alternate_do_string[5000]; +static int alternate_do_pointer; +static char alternate_do_string[5000]; DEFUN ("alternate-debugging-output", Falternate_debugging_output, 1, 1, 0, /* Append CHARACTER to the array `alternate_do_string'. @@ -1467,7 +1462,6 @@ /* Debugging kludge -- unbuffered */ static int debug_print_length = 50; static int debug_print_level = 15; -Lisp_Object debug_temp; static void debug_print_no_newline (Lisp_Object debug_print_obj) @@ -1604,15 +1598,8 @@ void syms_of_print (void) { - defsymbol (&Qprint_escape_newlines, "print-escape-newlines"); - defsymbol (&Qprint_readably, "print-readably"); - defsymbol (&Qstandard_output, "standard-output"); -#ifdef LISP_FLOAT_TYPE - defsymbol (&Qfloat_output_format, "float-output-format"); -#endif - defsymbol (&Qprint_length, "print-length"); defsymbol (&Qprint_string_length, "print-string-length"); @@ -1629,7 +1616,6 @@ DEFSUBR (Fterpri); DEFSUBR (Fwrite_char); DEFSUBR (Falternate_debugging_output); - defsymbol (&Qalternate_debugging_output, "alternate-debugging-output"); DEFSUBR (Fexternal_debugging_output); DEFSUBR (Fopen_termscript); defsymbol (&Qexternal_debugging_output, "external-debugging-output"); @@ -1637,9 +1623,15 @@ } void +reinit_vars_of_print (void) +{ + alternate_do_pointer = 0; +} + +void vars_of_print (void) { - alternate_do_pointer = 0; + reinit_vars_of_print (); DEFVAR_LISP ("standard-output", &Vstandard_output /* Output stream `print' uses by default for outputting a character. diff -r 28d9c139be4c -r 11054d720c21 src/process-nt.c --- a/src/process-nt.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/process-nt.c Mon Aug 13 11:26:11 2007 +0200 @@ -409,8 +409,6 @@ * must signal an error instead. */ -/* #### This function completely ignores Vprocess_environment */ - static void signal_cannot_launch (Lisp_Object image_file, DWORD err) { @@ -426,6 +424,7 @@ HANDLE hmyshove, hmyslurp, hprocin, hprocout; LPTSTR command_line; BOOL do_io, windowed; + char *proc_env; /* Find out whether the application is windowed or not */ { @@ -513,6 +512,80 @@ UNGCPRO; /* args_or_ret */ } + /* Set `proc_env' to a nul-separated array of the strings in + Vprocess_environment terminated by 2 nuls. */ + + { + extern int compare_env (const char **strp1, const char **strp2); + char **env; + REGISTER Lisp_Object tem; + REGISTER char **new_env; + REGISTER int new_length = 0, i, new_space; + char *penv; + + for (tem = Vprocess_environment; + (CONSP (tem) + && STRINGP (XCAR (tem))); + tem = XCDR (tem)) + new_length++; + + /* new_length + 1 to include terminating 0. */ + env = new_env = alloca_array (char *, new_length + 1); + + /* Copy the Vprocess_environment strings into new_env. */ + for (tem = Vprocess_environment; + (CONSP (tem) + && STRINGP (XCAR (tem))); + tem = XCDR (tem)) + { + char **ep = env; + char *string = (char *) XSTRING_DATA (XCAR (tem)); + /* See if this string duplicates any string already in the env. + If so, don't put it in. + When an env var has multiple definitions, + we keep the definition that comes first in process-environment. */ + for (; ep != new_env; ep++) + { + char *p = *ep, *q = string; + while (1) + { + if (*q == 0) + /* The string is malformed; might as well drop it. */ + goto duplicate; + if (*q != *p) + break; + if (*q == '=') + goto duplicate; + p++, q++; + } + } + *new_env++ = string; + duplicate: ; + } + *new_env = 0; + + /* Sort the environment variables */ + new_length = new_env - env; + qsort (env, new_length, sizeof (char *), compare_env); + + /* Work out how much space to allocate */ + new_space = 0; + for (i = 0; i < new_length; i++) + { + new_space += strlen(env[i]) + 1; + } + new_space++; + + /* Allocate space and copy variables into it */ + penv = proc_env = alloca(new_space); + for (i = 0; i < new_length; i++) + { + strcpy(penv, env[i]); + penv += strlen(env[i]) + 1; + } + *penv = 0; + } + /* Create process */ { STARTUPINFO si; @@ -533,7 +606,7 @@ err = (CreateProcess (NULL, command_line, NULL, NULL, TRUE, CREATE_NEW_CONSOLE | CREATE_NEW_PROCESS_GROUP | CREATE_SUSPENDED, - NULL, (char *) XSTRING_DATA (cur_dir), &si, &pi) + proc_env, (char *) XSTRING_DATA (cur_dir), &si, &pi) ? 0 : GetLastError ()); if (do_io) @@ -834,7 +907,7 @@ static void nt_open_network_stream (Lisp_Object name, Lisp_Object host, Lisp_Object service, - Lisp_Object family, void** vinfd, void** voutfd) + Lisp_Object protocol, void** vinfd, void** voutfd) { struct sockaddr_in address; SOCKET s; @@ -843,9 +916,9 @@ CHECK_STRING (host); - if (!EQ (family, Qtcpip)) - error ("Unsupported protocol family \"%s\"", - string_data (symbol_name (XSYMBOL (family)))); + if (!EQ (protocol, Qtcp)) + error ("Unsupported protocol \"%s\"", + string_data (symbol_name (XSYMBOL (protocol)))); if (INTP (service)) port = htons ((unsigned short) XINT (service)); diff -r 28d9c139be4c -r 11054d720c21 src/process-unix.c --- a/src/process-unix.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/process-unix.c Mon Aug 13 11:26:11 2007 +0200 @@ -212,9 +212,11 @@ end of the ptys. */ int failed_count = 0; #endif + int fd; +#ifndef HAVE_GETPT int i; - int fd; int c; +#endif #ifdef PTY_ITERATION PTY_ITERATION @@ -261,7 +263,7 @@ #else sprintf (pty_name, "/dev/tty%c%x", c, i); #endif /* no PTY_TTY_NAME_SPRINTF */ -#ifndef UNIPLUS +#if !defined(UNIPLUS) && !defined(HAVE_GETPT) if (access (pty_name, 6) != 0) { close (fd); @@ -384,7 +386,7 @@ else continue; } - else if ((INTP (tail_port)) && (htons ((unsigned short) XINT (tail_port)) == port)) + else if (INTP (tail_port) && (htons ((unsigned short) XINT (tail_port)) == port)) break; } @@ -663,10 +665,9 @@ */ static void -unix_mark_process_data (struct Lisp_Process *proc, - void (*markobj) (Lisp_Object)) +unix_mark_process_data (struct Lisp_Process *proc) { - markobj (UNIX_DATA(proc)->tty_name); + mark_object (UNIX_DATA(proc)->tty_name); } /* @@ -1429,19 +1430,21 @@ static void unix_open_network_stream (Lisp_Object name, Lisp_Object host, Lisp_Object service, - Lisp_Object family, void** vinfd, void** voutfd) + Lisp_Object protocol, void** vinfd, void** voutfd) { struct sockaddr_in address; - int s, inch, outch; + int inch; + int outch; + volatile int s; volatile int port; volatile int retry = 0; int retval; CHECK_STRING (host); - if (!EQ (family, Qtcpip)) - error ("Unsupported protocol family \"%s\"", - string_data (symbol_name (XSYMBOL (family)))); + if (!EQ (protocol, Qtcp) && !EQ (protocol, Qudp)) + error ("Unsupported protocol \"%s\"", + string_data (symbol_name (XSYMBOL (protocol)))); if (INTP (service)) port = htons ((unsigned short) XINT (service)); @@ -1449,7 +1452,12 @@ { struct servent *svc_info; CHECK_STRING (service); - svc_info = getservbyname ((char *) XSTRING_DATA (service), "tcp"); + + if (EQ (protocol, Qtcp)) + svc_info = getservbyname ((char *) XSTRING_DATA (service), "tcp"); + else /* EQ (protocol, Qudp) */ + svc_info = getservbyname ((char *) XSTRING_DATA (service), "udp"); + if (svc_info == 0) error ("Unknown service \"%s\"", XSTRING_DATA (service)); port = svc_info->s_port; @@ -1458,7 +1466,11 @@ get_internet_address (host, &address, ERROR_ME); address.sin_port = port; - s = socket (address.sin_family, SOCK_STREAM, 0); + if (EQ (protocol, Qtcp)) + s = socket (address.sin_family, SOCK_STREAM, 0); + else /* EQ (protocol, Qudp) */ + s = socket (address.sin_family, SOCK_DGRAM, 0); + if (s < 0) report_file_error ("error creating socket", list1 (name)); diff -r 28d9c139be4c -r 11054d720c21 src/process.c --- a/src/process.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/process.c Mon Aug 13 11:26:11 2007 +0200 @@ -71,7 +71,7 @@ /* Qrun => Qopen, Qexit => Qclosed for "network connection" processes */ Lisp_Object Qopen, Qclosed; /* Protocol families */ -Lisp_Object Qtcpip; +Lisp_Object Qtcp, Qudp; #ifdef HAVE_MULTICAST Lisp_Object Qmulticast; /* Will be used for occasional warnings */ @@ -111,22 +111,22 @@ static Lisp_Object -mark_process (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_process (Lisp_Object obj) { struct Lisp_Process *proc = XPROCESS (obj); - MAYBE_PROCMETH (mark_process_data, (proc, markobj)); - markobj (proc->name); - markobj (proc->command); - markobj (proc->filter); - markobj (proc->sentinel); - markobj (proc->buffer); - markobj (proc->mark); - markobj (proc->pid); - markobj (proc->pipe_instream); - markobj (proc->pipe_outstream); + MAYBE_PROCMETH (mark_process_data, (proc)); + mark_object (proc->name); + mark_object (proc->command); + mark_object (proc->filter); + mark_object (proc->sentinel); + mark_object (proc->buffer); + mark_object (proc->mark); + mark_object (proc->pid); + mark_object (proc->pipe_instream); + mark_object (proc->pipe_outstream); #ifdef FILE_CODING - markobj (proc->coding_instream); - markobj (proc->coding_outstream); + mark_object (proc->coding_instream); + mark_object (proc->coding_outstream); #endif return proc->status_symbol; } @@ -245,7 +245,7 @@ int network_connection_p (Lisp_Object process) { - return GC_CONSP (XPROCESS (process)->pid); + return CONSP (XPROCESS (process)->pid); } #endif @@ -272,7 +272,7 @@ { Lisp_Object tail; - if (GC_PROCESSP (name)) + if (PROCESSP (name)) return name; if (!gc_in_progress) @@ -280,7 +280,7 @@ of a signal or crash. */ CHECK_STRING (name); - for (tail = Vprocess_list; GC_CONSP (tail); tail = XCDR (tail)) + for (tail = Vprocess_list; CONSP (tail); tail = XCDR (tail)) { Lisp_Object proc = XCAR (tail); QUIT; @@ -298,18 +298,18 @@ { Lisp_Object buf, tail, proc; - if (GC_NILP (name)) return Qnil; + if (NILP (name)) return Qnil; buf = Fget_buffer (name); - if (GC_NILP (buf)) return Qnil; + if (NILP (buf)) return Qnil; - for (tail = Vprocess_list; GC_CONSP (tail); tail = XCDR (tail)) + for (tail = Vprocess_list; CONSP (tail); tail = XCDR (tail)) { /* jwz: do not quit here - it isn't necessary, as there is no way for Vprocess_list to get circular or overwhelmingly long, and this function is called from layout_mode_element under redisplay. */ /* QUIT; */ proc = XCAR (tail); - if (GC_PROCESSP (proc) && EQ (XPROCESS (proc)->buffer, buf)) + if (PROCESSP (proc) && EQ (XPROCESS (proc)->buffer, buf)) return proc; } return Qnil; @@ -331,28 +331,28 @@ /* This may be called during a GC from process_send_signal() from kill_buffer_processes() if emacs decides to abort(). */ - if (GC_PROCESSP (name)) + if (PROCESSP (name)) return name; - if (GC_STRINGP (name)) + if (STRINGP (name)) { obj = Fget_process (name); - if (GC_NILP (obj)) + if (NILP (obj)) obj = Fget_buffer (name); - if (GC_NILP (obj)) + if (NILP (obj)) error ("Process %s does not exist", XSTRING_DATA (name)); } - else if (GC_NILP (name)) + else if (NILP (name)) obj = Fcurrent_buffer (); else obj = name; /* Now obj should be either a buffer object or a process object. */ - if (GC_BUFFERP (obj)) + if (BUFFERP (obj)) { proc = Fget_buffer_process (obj); - if (GC_NILP (proc)) + if (NILP (proc)) error ("Buffer %s has no process", XSTRING_DATA (XBUFFER(obj)->name)); } else @@ -659,7 +659,7 @@ DEFUN ("open-network-stream-internal", Fopen_network_stream_internal, 4, 5, 0, /* Open a TCP connection for a service to a host. -Returns a subprocess-object to represent the connection. +Return a subprocess-object to represent the connection. Input and output work as for subprocesses; `delete-process' closes it. NAME is name for process. It is modified if necessary to make it unique. @@ -671,10 +671,18 @@ Third arg is name of the host to connect to, or its IP address. Fourth arg SERVICE is name of the service desired, or an integer specifying a port number to connect to. -Fifth argument FAMILY is a protocol family. When omitted, 'tcp/ip -\(Internet protocol family TCP/IP) is assumed. +Fifth argument PROTOCOL is a network protocol. Currently 'tcp + (Transmission Control Protocol) and 'udp (User Datagram Protocol) are + supported. When omitted, 'tcp is assumed. + +Ouput via `process-send-string' and input via buffer or filter (see +`set-process-filter') are stream-oriented. That means UDP datagrams are +not guaranteed to be sent and received in discrete packets. (But small +datagrams around 500 bytes that are not truncated by `process-send-string' +are usually fine.) Note further that UDP protocol does not guard against +lost packets. */ - (name, buffer, host, service, family)) + (name, buffer, host, service, protocol)) { /* !!#### This function has not been Mule-ized */ /* This function can GC */ @@ -682,17 +690,17 @@ struct gcpro gcpro1, gcpro2, gcpro3, gcpro4, gcpro5, ngcpro1; void *inch, *outch; - GCPRO5 (name, buffer, host, service, family); + GCPRO5 (name, buffer, host, service, protocol); CHECK_STRING (name); - if (NILP(family)) - family = Qtcpip; + if (NILP(protocol)) + protocol = Qtcp; else - CHECK_SYMBOL (family); + CHECK_SYMBOL (protocol); /* Since this code is inside HAVE_SOCKETS, existence of open_network_stream is mandatory */ - PROCMETH (open_network_stream, (name, host, service, family, + PROCMETH (open_network_stream, (name, host, service, protocol, &inch, &outch)); if (!NILP (buffer)) @@ -716,7 +724,7 @@ DEFUN ("open-multicast-group-internal", Fopen_multicast_group_internal, 5, 5, 0, /* Open a multicast connection on the specified dest/port/ttl. -Returns a subprocess-object to represent the connection. +Return a subprocess-object to represent the connection. Input and output work as for subprocesses; `delete-process' closes it. NAME is name for process. It is modified if necessary to make it unique. @@ -965,7 +973,7 @@ if (nonrelocatable) lstream = make_fixed_buffer_input_stream (nonrelocatable + start, len); - else if (GC_BUFFERP (relocatable)) + else if (BUFFERP (relocatable)) lstream = make_lisp_buffer_input_stream (XBUFFER (relocatable), start, start + len, 0); else @@ -1898,12 +1906,12 @@ { Lisp_Object tail; - for (tail = Vprocess_list; GC_CONSP (tail); + for (tail = Vprocess_list; CONSP (tail); tail = XCDR (tail)) { Lisp_Object proc = XCAR (tail); - if (GC_PROCESSP (proc) - && (GC_NILP (buffer) || GC_EQ (XPROCESS (proc)->buffer, buffer))) + if (PROCESSP (proc) + && (NILP (buffer) || EQ (XPROCESS (proc)->buffer, buffer))) { if (network_connection_p (proc)) Fdelete_process (proc); @@ -1975,7 +1983,8 @@ defsymbol (&Qopen, "open"); defsymbol (&Qclosed, "closed"); - defsymbol (&Qtcpip, "tcp/ip"); + defsymbol (&Qtcp, "tcp"); + defsymbol (&Qudp, "udp"); #ifdef HAVE_MULTICAST defsymbol(&Qmulticast, "multicast"); /* Used for occasional warnings */ diff -r 28d9c139be4c -r 11054d720c21 src/process.h --- a/src/process.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/process.h Mon Aug 13 11:26:11 2007 +0200 @@ -44,7 +44,6 @@ #define XPROCESS(x) XRECORD (x, process, struct Lisp_Process) #define XSETPROCESS(x, p) XSETRECORD (x, p, process) #define PROCESSP(x) RECORDP (x, process) -#define GC_PROCESSP(x) GC_RECORDP (x, process) #define CHECK_PROCESS(x) CHECK_RECORD (x, process) #define PROCESS_LIVE_P(x) (!NILP (XPROCESS(x)->pipe_instream)) @@ -93,7 +92,7 @@ #define network_connection_p(x) 0 #endif -extern Lisp_Object Qclosed, Qmulticast, Qopen, Qrun, Qstop, Qtcpip; +extern Lisp_Object Qclosed, Qmulticast, Qopen, Qrun, Qstop, Qtcp, Qudp; extern Lisp_Object Vprocess_connection_type, Vprocess_list; /* Report all recent events of a change in process status @@ -134,4 +133,13 @@ #endif /* emacs */ +#ifdef HAVE_GETPT +#define PTY_ITERATION +#define PTY_OPEN \ + if ((fd = getpt()) < 0 || grantpt (fd) < 0 || unlockpt (fd) < 0) \ + return -1; +#define PTY_NAME_SPRINTF +#define PTY_TTY_NAME_SPRINTF strcpy (pty_name, ptsname (fd)); +#endif + #endif /* _XEMACS_PROCESS_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/procimpl.h --- a/src/procimpl.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/procimpl.h Mon Aug 13 11:26:11 2007 +0200 @@ -37,8 +37,7 @@ struct process_methods { - void (*mark_process_data) (struct Lisp_Process *proc, - void (*markobj) (Lisp_Object)); + void (*mark_process_data) (struct Lisp_Process *proc); void (*print_process_data) (struct Lisp_Process *proc, Lisp_Object printcharfun); void (*finalize_process_data) (struct Lisp_Process *proc, int for_disksave); @@ -51,7 +50,7 @@ int (*tooltalk_connection_p) (struct Lisp_Process *p); #ifdef HAVE_SOCKETS void (*open_network_stream) (Lisp_Object name, Lisp_Object host, - Lisp_Object service, Lisp_Object family, + Lisp_Object service, Lisp_Object protocol, void** vinfd, void** voutfd); #ifdef HAVE_MULTICAST void (*open_multicast_group) (Lisp_Object name, Lisp_Object dest, @@ -159,7 +158,7 @@ /* Random externs from process.c */ extern Lisp_Object Qrun, Qstop, Qopen, Qclosed; -extern Lisp_Object Qtcpip; +extern Lisp_Object Qtcp, Qudp; extern Lisp_Object Vprocess_connection_type; extern Lisp_Object Vprocess_list; diff -r 28d9c139be4c -r 11054d720c21 src/profile.c --- a/src/profile.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/profile.c Mon Aug 13 11:26:11 2007 +0200 @@ -57,7 +57,7 @@ even be useful to provide a way to turn on only one profiling mechanism, but I haven't done so yet. --hniksic */ -struct hash_table *big_profile_table; +static struct hash_table *big_profile_table; Lisp_Object Vcall_count_profile_table; int default_profiling_interval; @@ -68,10 +68,10 @@ and is not set the whole time we're in redisplay. */ int profiling_redisplay_flag; -Lisp_Object QSin_redisplay; -Lisp_Object QSin_garbage_collection; -Lisp_Object QSprocessing_events_at_top_level; -Lisp_Object QSunknown; +static Lisp_Object QSin_redisplay; +static Lisp_Object QSin_garbage_collection; +static Lisp_Object QSprocessing_events_at_top_level; +static Lisp_Object QSunknown; /* We use inside_profiling to prevent the handler from writing to the table while another routine is operating on it. We also set @@ -119,9 +119,9 @@ { fun = *backtrace_list->function; - if (!GC_SYMBOLP (fun) && - !GC_COMPILED_FUNCTIONP (fun) && - !GC_SUBRP (fun)) + if (!SYMBOLP (fun) && + !COMPILED_FUNCTIONP (fun) && + !SUBRP (fun)) fun = QSunknown; } else @@ -262,11 +262,6 @@ return closure.accum; } -struct mark_profiling_info_closure -{ - void (*markfun) (Lisp_Object); -}; - static int mark_profiling_info_maphash (CONST void *void_key, void *void_val, @@ -275,21 +270,18 @@ Lisp_Object key; CVOID_TO_LISP (key, void_key); - (((struct mark_profiling_info_closure *) void_closure)->markfun) (key); + mark_object (key); return 0; } void -mark_profiling_info (void (*markfun) (Lisp_Object)) +mark_profiling_info (void) { - /* This function does not GC (if markfun doesn't) */ - struct mark_profiling_info_closure closure; - - closure.markfun = markfun; + /* This function does not GC */ if (big_profile_table) { inside_profiling = 1; - maphash (mark_profiling_info_maphash, big_profile_table, &closure); + maphash (mark_profiling_info_maphash, big_profile_table, 0); inside_profiling = 0; } } diff -r 28d9c139be4c -r 11054d720c21 src/ralloc.c --- a/src/ralloc.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/ralloc.c Mon Aug 13 11:26:11 2007 +0200 @@ -98,7 +98,7 @@ /* Declarations for working with the malloc, ralloc, and system breaks. */ /* Function to set the real break value. */ -static POINTER (*real_morecore) (long size); +static POINTER (*real_morecore) (ptrdiff_t size); /* The break value, as seen by malloc (). */ static POINTER virtual_break_value; @@ -339,7 +339,7 @@ If SIZE is more than a page, return the space to the system. */ static void -relinquish () +relinquish (void) { register heap_ptr h; int excess = 0; @@ -790,9 +790,9 @@ __morecore hook values - in particular, __default_morecore in the GNU malloc package. */ -POINTER r_alloc_sbrk (long size); +POINTER r_alloc_sbrk (ptrdiff_t size); POINTER -r_alloc_sbrk (long size) +r_alloc_sbrk (ptrdiff_t size) { register bloc_ptr b; POINTER address; @@ -1082,7 +1082,7 @@ void r_alloc_thaw (void); void -r_alloc_thaw () +r_alloc_thaw (void) { if (! r_alloc_initialized) @@ -1109,14 +1109,11 @@ /* The hook `malloc' uses for the function which gets more space from the system. */ #ifndef DOUG_LEA_MALLOC -extern POINTER (*__morecore) (long size); +extern POINTER (*__morecore) (ptrdiff_t size); #endif /* Initialize various things for memory allocation. */ -#define SET_FUN_PTR(fun_ptr, fun_val) \ - (*((void **) (&fun_ptr)) = ((void *) (fun_val))) - void init_ralloc (void) { @@ -1124,8 +1121,12 @@ return; r_alloc_initialized = 1; - SET_FUN_PTR (real_morecore, __morecore); - SET_FUN_PTR (__morecore, r_alloc_sbrk); + real_morecore = (POINTER (*) (ptrdiff_t)) __morecore; + __morecore = +#ifdef __GNUC__ + (__typeof__ (__morecore)) +#endif + r_alloc_sbrk; first_heap = last_heap = &heap_base; first_heap->next = first_heap->prev = NIL_HEAP; @@ -1172,21 +1173,25 @@ Emacs. This is needed when using Doug Lea's malloc from GNU libc. */ void r_alloc_reinit (void); void -r_alloc_reinit () +r_alloc_reinit (void) { /* Only do this if the hook has been reset, so that we don't get an infinite loop, in case Emacs was linked statically. */ - if ( ((void*) __morecore) != (void *) (r_alloc_sbrk)) + if ( (POINTER (*) (ptrdiff_t)) __morecore != r_alloc_sbrk) { - SET_FUN_PTR (real_morecore, __morecore); - SET_FUN_PTR (__morecore, r_alloc_sbrk); + real_morecore = (POINTER (*) (ptrdiff_t)) __morecore; + __morecore = +#ifdef __GNUC__ + (__typeof__ (__morecore)) +#endif + r_alloc_sbrk; } } #if 0 #ifdef DEBUG void -r_alloc_check () +r_alloc_check (void) { int found = 0; heap_ptr h, ph = 0; diff -r 28d9c139be4c -r 11054d720c21 src/rangetab.c --- a/src/rangetab.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/rangetab.c Mon Aug 13 11:26:11 2007 +0200 @@ -41,13 +41,13 @@ is not hard but just requires moving that stuff out of that file. */ static Lisp_Object -mark_range_table (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_range_table (Lisp_Object obj) { struct Lisp_Range_Table *rt = XRANGE_TABLE (obj); int i; for (i = 0; i < Dynarr_length (rt->entries); i++) - markobj (Dynarr_at (rt->entries, i).val); + mark_object (Dynarr_at (rt->entries, i).val); return Qnil; } @@ -132,9 +132,35 @@ return hash; } +static const struct lrecord_description rte_description_1[] = { + { XD_LISP_OBJECT, offsetof(range_table_entry, val), 1 }, + { XD_END } +}; + +static const struct struct_description rte_description = { + sizeof(range_table_entry), + rte_description_1 +}; + +static const struct lrecord_description rted_description_1[] = { + XD_DYNARR_DESC(range_table_entry_dynarr, &rte_description), + { XD_END } +}; + +static const struct struct_description rted_description = { + sizeof(range_table_entry_dynarr), + rted_description_1 +}; + +static const struct lrecord_description range_table_description[] = { + { XD_STRUCT_PTR, offsetof(struct Lisp_Range_Table, entries), 1, &rted_description }, + { XD_END } +}; + DEFINE_LRECORD_IMPLEMENTATION ("range-table", range_table, mark_range_table, print_range_table, 0, - range_table_equal, range_table_hash, 0, + range_table_equal, range_table_hash, + range_table_description, struct Lisp_Range_Table); /************************************************************************/ diff -r 28d9c139be4c -r 11054d720c21 src/rangetab.h --- a/src/rangetab.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/rangetab.h Mon Aug 13 11:26:11 2007 +0200 @@ -50,7 +50,6 @@ XRECORD (x, range_table, struct Lisp_Range_Table) #define XSETRANGE_TABLE(x, p) XSETRECORD (x, p, range_table) #define RANGE_TABLEP(x) RECORDP (x, range_table) -#define GC_RANGE_TABLEP(x) GC_RECORDP (x, range_table) #define CHECK_RANGE_TABLE(x) CHECK_RECORD (x, range_table) #endif diff -r 28d9c139be4c -r 11054d720c21 src/realpath.c --- a/src/realpath.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/realpath.c Mon Aug 13 11:26:11 2007 +0200 @@ -22,25 +22,20 @@ /* Synched up with: Not in FSF. */ -#ifdef HAVE_CONFIG_H #include -#endif #include -#if defined(HAVE_UNISTD_H) || defined(STDC_HEADERS) +#include +#include +#include +#ifdef HAVE_UNISTD_H #include #endif -#include -#include #ifdef _POSIX_VERSION #include /* for PATH_MAX */ #else #include /* for MAXPATHLEN */ #endif -#include -#ifndef STDC_HEADERS -extern int errno; -#endif #ifdef WINDOWSNT #include @@ -62,13 +57,8 @@ #define MAX_READLINKS 32 -#ifdef __STDC__ -char *xrealpath(const char *path, char resolved_path []) -#else -char *xrealpath(path, resolved_path) -const char *path; -char resolved_path []; -#endif +char * +xrealpath (const char *path, char resolved_path []) { char copy_path[PATH_MAX]; char *new_path = resolved_path; diff -r 28d9c139be4c -r 11054d720c21 src/redisplay-msw.c --- a/src/redisplay-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/redisplay-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -64,19 +64,8 @@ int y, int width, int height); static void mswindows_output_dibitmap (struct frame *f, struct Lisp_Image_Instance *p, - int x, int y, - int clip_x, int clip_y, - int clip_width, int clip_height, - int width, int height, - int pixmap_offset, - int offset_bitmap); -static void mswindows_output_pixmap (struct window *w, struct display_line *dl, - Lisp_Object image_instance, int xpos, - int xoffset, int start_pixpos, int width, - face_index findex, int cursor_start, - int cursor_width, int cursor_height, - int offset_bitmap); -void bevel_modeline (struct window *w, struct display_line *dl); + struct display_box* db, + struct display_glyph_area* dga); typedef struct textual_run { @@ -304,28 +293,37 @@ of its face. ****************************************************************************/ static void -mswindows_output_blank (struct window *w, struct display_line *dl, struct rune *rb, int start_pixpos) +mswindows_output_blank (struct window *w, struct display_line *dl, + struct rune *rb, int start_pixpos) { struct frame *f = XFRAME (w->frame); - RECT rect = { rb->xpos, dl->ypos-dl->ascent, - rb->xpos+rb->width, dl->ypos+dl->descent-dl->clip }; + RECT rect = { rb->xpos, DISPLAY_LINE_YPOS (dl), + rb->xpos+rb->width, + DISPLAY_LINE_YEND (dl) }; struct face_cachel *cachel = WINDOW_FACE_CACHEL (w, rb->findex); Lisp_Object bg_pmap = WINDOW_FACE_CACHEL_BACKGROUND_PIXMAP (w, rb->findex); + /* Unmap all subwindows in the area we are going to blank. */ + redisplay_unmap_subwindows_maybe (f, rb->xpos, DISPLAY_LINE_YPOS (dl), + rb->width, DISPLAY_LINE_HEIGHT (dl)); + if (!IMAGE_INSTANCEP (bg_pmap) || !IMAGE_INSTANCE_PIXMAP_TYPE_P (XIMAGE_INSTANCE (bg_pmap))) bg_pmap = Qnil; if (!NILP(bg_pmap)) { + struct display_box db; + struct display_glyph_area dga; + redisplay_calculate_display_boxes (dl, rb->xpos, + /*rb->object.dglyph.xoffset*/ 0, + start_pixpos, rb->width, + &db, &dga); /* blank the background in the appropriate color */ mswindows_update_dc (FRAME_MSWINDOWS_DC (f), Qnil, cachel->foreground, cachel->background, Qnil); - - mswindows_output_pixmap (w, dl, bg_pmap, - rb->xpos, 0 /*rb->object.dglyph.xoffset*/, - start_pixpos, rb->width, rb->findex, + redisplay_output_pixmap (w, bg_pmap, &db, &dga, rb->findex, 0, 0, 0, TRUE); } else @@ -359,15 +357,19 @@ char *p_char = NULL; int n_char = 0; RECT rect = { xpos, - dl->ypos - dl->ascent, + DISPLAY_LINE_YPOS (dl), xpos + width, - dl->ypos + dl->descent - dl->clip}; + DISPLAY_LINE_YEND (dl) }; Lisp_Object bar = symbol_value_in_buffer (Qbar_cursor, WINDOW_BUFFER (w)); int bar_p = image_p || !NILP (bar); int cursor_p = !NILP (w->text_cursor_visible_p); int real_char_p = ch != 0; + /* Unmap all subwindows in the area we are going to blank. */ + redisplay_unmap_subwindows_maybe (f, xpos, DISPLAY_LINE_YPOS (dl), + width, DISPLAY_LINE_HEIGHT (dl)); + if (real_char_p) { /* Use the font from the underlying character */ @@ -466,8 +468,10 @@ ****************************************************************************/ void mswindows_output_string (struct window *w, struct display_line *dl, - Emchar_dynarr *buf, int xpos, int xoffset, int clip_start, - int width, face_index findex) + Emchar_dynarr *buf, int xpos, int xoffset, int clip_start, + int width, face_index findex, + int cursor, int cursor_start, int cursor_width, + int cursor_height) { struct frame *f = XFRAME (w->frame); /* struct device *d = XDEVICE (f->device);*/ @@ -506,9 +510,13 @@ /* sort out the destination rectangle */ height = DISPLAY_LINE_HEIGHT (dl); rect.left = clip_start; - rect.top = dl->ypos - dl->ascent; + rect.top = DISPLAY_LINE_YPOS (dl); rect.right = clip_end; - rect.bottom = height + dl->ypos - dl->ascent; + rect.bottom = rect.top + height; + + /* make sure the area we are about to display is subwindow free. */ + redisplay_unmap_subwindows_maybe (f, clip_start, DISPLAY_LINE_YPOS (dl), + clip_end - clip_start, DISPLAY_LINE_HEIGHT (dl)); /* output the background pixmap if there is one */ bg_pmap = cachel->background_pixmap; @@ -518,13 +526,14 @@ if (!NILP(bg_pmap)) { + struct display_box db; + struct display_glyph_area dga; + redisplay_calculate_display_boxes (dl, xpos + xoffset, 0, + clip_start, width, &db, &dga); /* blank the background in the appropriate color */ mswindows_update_dc (hdc, Qnil, cachel->foreground, cachel->background, Qnil); - - mswindows_output_pixmap (w, dl, bg_pmap, - xpos, xoffset, - clip_start, width, findex, + redisplay_output_pixmap (w, bg_pmap, &db, &dga, findex, 0, 0, 0, TRUE); /* output pixmap calls this so we have to recall to get correct references */ @@ -549,14 +558,14 @@ this_width = mswindows_text_width_single_run (hdc, cachel, runs + i); /* cope with fonts taller than lines */ - if ((int) fi->height < (int) (height + dl->clip)) + if ((int) fi->height < (int) (height + dl->clip + dl->top_clip)) { int clear_start = max (xpos, clip_start); int clear_end = min (xpos + this_width, clip_end); { redisplay_clear_region (window, findex, clear_start, - dl->ypos - dl->ascent, + DISPLAY_LINE_YPOS (dl), clear_end - clear_start, height); /* output pixmap calls this so we have to recall to get correct @@ -581,31 +590,12 @@ static void mswindows_output_dibitmap (struct frame *f, struct Lisp_Image_Instance *p, - int x, int y, - int clip_x, int clip_y, - int clip_width, int clip_height, - int width, int height, int pixmap_offset, - int offset_bitmap) + struct display_box* db, + struct display_glyph_area* dga) { HDC hdc = FRAME_MSWINDOWS_DC (f); HGDIOBJ old=NULL; COLORREF bgcolor = GetBkColor (hdc); - int need_clipping = (clip_x || clip_y); - int yoffset=0; - int xoffset=0; - - /* do we need to offset the pixmap vertically? this is necessary - for background pixmaps. */ - if (offset_bitmap) - { - yoffset = y % IMAGE_INSTANCE_PIXMAP_HEIGHT (p); - xoffset = x % IMAGE_INSTANCE_PIXMAP_WIDTH (p); - /* the width is handled by mswindows_output_pixmap_region */ - } - - if (need_clipping) - { - } /* first blt the mask */ if (IMAGE_INSTANCE_MSWINDOWS_MASK (p)) @@ -622,93 +612,94 @@ SetDIBColorTable (FRAME_MSWINDOWS_CDC (f), 1, 1, &col); BitBlt (hdc, - x,y, - width, height, + db->xpos, db->ypos, + dga->width, dga->height, FRAME_MSWINDOWS_CDC (f), - xoffset,yoffset, + dga->xoffset, dga->yoffset, SRCCOPY); SelectObject (FRAME_MSWINDOWS_CDC (f), old); } - /* now blt the bitmap itself. */ + /* Now blt the bitmap itself, or one of its slices. */ old = SelectObject (FRAME_MSWINDOWS_CDC (f), - IMAGE_INSTANCE_MSWINDOWS_BITMAP (p)); + IMAGE_INSTANCE_MSWINDOWS_BITMAP_SLICE + (p, IMAGE_INSTANCE_PIXMAP_SLICE (p))); BitBlt (hdc, - x,y, - width, height, + db->xpos, db->ypos, + dga->width, dga->height, FRAME_MSWINDOWS_CDC (f), - xoffset, yoffset, + dga->xoffset, dga->yoffset, IMAGE_INSTANCE_MSWINDOWS_MASK (p) ? SRCINVERT : SRCCOPY); SelectObject (FRAME_MSWINDOWS_CDC (f),old); - - if (need_clipping) - { - } } -/* - * X gc's have this nice property that setting the bg pixmap will +/* X gc's have this nice property that setting the bg pixmap will * output it offset relative to the window. Windows doesn't have this - * feature so we have to emulate this by outputting multiple pixmaps - */ + * feature so we have to emulate this by outputting multiple pixmaps. + * This is only used for background pixmaps. Normal pixmaps are + * outputted once and are scrollable */ static void mswindows_output_dibitmap_region (struct frame *f, struct Lisp_Image_Instance *p, - int x, int y, - int clip_x, int clip_y, - int clip_width, int clip_height, - int width, int height, int pixmap_offset, - int offset_bitmap) + struct display_box *db, + struct display_glyph_area *dga) { - int pwidth = min (width, IMAGE_INSTANCE_PIXMAP_WIDTH (p)); - int pheight = min (height, IMAGE_INSTANCE_PIXMAP_HEIGHT (p)); + struct display_box xdb = { db->xpos, db->ypos, db->width, db->height }; + struct display_glyph_area xdga + = { 0, 0, IMAGE_INSTANCE_PIXMAP_WIDTH (p), + IMAGE_INSTANCE_PIXMAP_HEIGHT (p) }; int pxoffset = 0, pyoffset = 0; + if (dga) + { + xdga.width = dga->width; + xdga.height = dga->height; + } + else if (!redisplay_normalize_glyph_area (&xdb, &xdga)) + return; + /* when doing a bg pixmap do a partial pixmap first so that we blt whole pixmaps thereafter */ + xdga.height = min (xdga.height, IMAGE_INSTANCE_PIXMAP_HEIGHT (p) - + db->ypos % IMAGE_INSTANCE_PIXMAP_HEIGHT (p)); - if (offset_bitmap) + while (xdga.height > 0) { - pheight = min (pheight, IMAGE_INSTANCE_PIXMAP_HEIGHT (p) - - y % IMAGE_INSTANCE_PIXMAP_HEIGHT (p)); - } - - while (pheight > 0) - { - if (offset_bitmap) + xdga.width = min (min (db->width, IMAGE_INSTANCE_PIXMAP_WIDTH (p)), + IMAGE_INSTANCE_PIXMAP_WIDTH (p) - + db->xpos % IMAGE_INSTANCE_PIXMAP_WIDTH (p)); + pxoffset = 0; + while (xdga.width > 0) { - pwidth = min (min (width, IMAGE_INSTANCE_PIXMAP_WIDTH (p)), - IMAGE_INSTANCE_PIXMAP_WIDTH (p) - - x % IMAGE_INSTANCE_PIXMAP_WIDTH (p)); - pxoffset = 0; + xdb.xpos = db->xpos + pxoffset; + xdb.ypos = db->ypos + pyoffset; + /* do we need to offset the pixmap vertically? this is necessary + for background pixmaps. */ + xdga.yoffset = xdb.ypos % IMAGE_INSTANCE_PIXMAP_HEIGHT (p); + xdga.xoffset = xdb.xpos % IMAGE_INSTANCE_PIXMAP_WIDTH (p); + /* the width is handled by mswindows_output_pixmap_region */ + mswindows_output_dibitmap (f, p, &xdb, &xdga); + pxoffset += xdga.width; + xdga.width = min ((db->width - pxoffset), + IMAGE_INSTANCE_PIXMAP_WIDTH (p)); } - while (pwidth > 0) - { - mswindows_output_dibitmap (f, p, - x + pxoffset, y + pyoffset, - clip_x, clip_y, - clip_width, clip_height, - pwidth, pheight, pixmap_offset, - offset_bitmap); - pxoffset += pwidth; - pwidth = min ((width-pxoffset), - IMAGE_INSTANCE_PIXMAP_WIDTH (p)); - } - pyoffset += pheight; - pheight = min ((height-pyoffset), - IMAGE_INSTANCE_PIXMAP_HEIGHT (p)); + pyoffset += xdga.height; + xdga.height = min ((db->height - pyoffset), + IMAGE_INSTANCE_PIXMAP_HEIGHT (p)); } } +/* Output a pixmap at the desired location. + DB normalized display_box. + DGA normalized display_glyph_area. */ static void -mswindows_output_pixmap (struct window *w, struct display_line *dl, - Lisp_Object image_instance, int xpos, int xoffset, - int start_pixpos, int width, face_index findex, - int cursor_start, int cursor_width, int cursor_height, - int offset_bitmap) +mswindows_output_pixmap (struct window *w, Lisp_Object image_instance, + struct display_box *db, struct display_glyph_area *dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height, int bg_pixmap) { struct frame *f = XFRAME (w->frame); HDC hdc = FRAME_MSWINDOWS_DC (f); @@ -716,100 +707,18 @@ struct Lisp_Image_Instance *p = XIMAGE_INSTANCE (image_instance); Lisp_Object window; - int lheight = DISPLAY_LINE_HEIGHT (dl); - int pheight = ((int) IMAGE_INSTANCE_PIXMAP_HEIGHT (p) > lheight ? lheight : - IMAGE_INSTANCE_PIXMAP_HEIGHT (p)); - int clip_x, clip_y, clip_width, clip_height; - - /* The pixmap_offset is used to center the pixmap on lines which are - shorter than it is. This results in odd effects when scrolling - pixmaps off of the bottom. Let's try not using it. */ -#if 0 - int pixmap_offset = (int) (IMAGE_INSTANCE_PIXMAP_HEIGHT (p) - lheight) / 2; -#else - int pixmap_offset = 0; -#endif - XSETWINDOW (window, w); - if ((start_pixpos >= 0 && start_pixpos > xpos) || xoffset) - { - if (start_pixpos > xpos && start_pixpos > xpos + width) - return; - - clip_x = xoffset; - clip_width = width; - if (start_pixpos > xpos) - { - clip_x += (start_pixpos - xpos); - clip_width -= (start_pixpos - xpos); - } - } - else - { - clip_x = 0; - clip_width = 0; - } - - /* Place markers for possible future functionality (clipping the top - half instead of the bottom half; think pixel scrolling). */ - clip_y = 0; - clip_height = pheight; - - /* Clear the area the pixmap is going into. The pixmap itself will - always take care of the full width. We don't want to clear where - it is going to go in order to avoid flicker. So, all we have to - take care of is any area above or below the pixmap. */ - /* #### We take a shortcut for now. We know that since we have - pixmap_offset hardwired to 0 that the pixmap is against the top - edge so all we have to worry about is below it. */ - /* #### Unless the pixmap has a mask in which case we have to clear - the whole damn thing since we can't yet clear just the area not - included in the mask. */ - if (((int) (dl->ypos - dl->ascent + pheight) < - (int) (dl->ypos + dl->descent - dl->clip)) - || IMAGE_INSTANCE_MSWINDOWS_MASK (p)) - { - int clear_x, clear_y, clear_width, clear_height; - - if (IMAGE_INSTANCE_MSWINDOWS_MASK (p)) - { - clear_y = dl->ypos - dl->ascent; - clear_height = lheight; - } - else - { - clear_y = dl->ypos - dl->ascent + pheight; - clear_height = lheight - pheight; - } - - if (start_pixpos >= 0 && start_pixpos > xpos) - { - clear_x = start_pixpos; - clear_width = xpos + width - start_pixpos; - } - else - { - clear_x = xpos; - clear_width = width; - } - - if (!offset_bitmap) /* i.e. not a bg pixmap */ - redisplay_clear_region (window, findex, clear_x, clear_y, - clear_width, clear_height); - } - /* Output the pixmap. Have to do this as many times as is required to fill the given area */ mswindows_update_dc (hdc, Qnil, WINDOW_FACE_CACHEL_FOREGROUND (w, findex), WINDOW_FACE_CACHEL_BACKGROUND (w, findex), Qnil); - mswindows_output_dibitmap_region (f, p, xpos - xoffset, - dl->ypos - dl->ascent, - clip_x, clip_y, clip_width, clip_height, - width + xoffset, pheight, pixmap_offset, - offset_bitmap); + if (bg_pixmap) + mswindows_output_dibitmap_region (f, p, db, dga); + else + mswindows_output_dibitmap (f, p, db, dga); } #ifdef HAVE_SCROLLBARS @@ -901,12 +810,11 @@ for (line = 0; line < Dynarr_length (cdla); line++) { struct display_line *cdl = Dynarr_atp (cdla, line); - int top_y = cdl->ypos - cdl->ascent; - int bottom_y = cdl->ypos + cdl->descent; - if (bottom_y >= rect_draw.top) + if (DISPLAY_LINE_YPOS (cdl) + DISPLAY_LINE_HEIGHT (cdl) + >= rect_draw.top) { - if (top_y > rect_draw.bottom) + if (DISPLAY_LINE_YPOS (cdl) > rect_draw.bottom) { if (line == 0) continue; @@ -986,29 +894,47 @@ ****************************************************************************/ static void mswindows_bevel_area (struct window *w, face_index findex, int x, int y, - int width, int height, int shadow_thickness) + int width, int height, int thickness, + int edges, enum edge_style style) { struct frame *f = XFRAME (w->frame); UINT edge; + UINT border = 0; - if (shadow_thickness < -1) - edge = EDGE_SUNKEN; - else if (shadow_thickness < 0) - edge = BDR_SUNKENINNER; - else if (shadow_thickness == 1) - edge = BDR_RAISEDINNER; - else - edge = EDGE_RAISED; + if (style == EDGE_ETCHED_IN) + edge = EDGE_ETCHED; + else if (style == EDGE_ETCHED_OUT) + edge = EDGE_BUMP; + else if (style == EDGE_BEVEL_IN) + { + if (thickness == 1) + edge = BDR_SUNKENINNER; + else + edge = EDGE_SUNKEN; + } + else /* EDGE_BEVEL_OUT */ + { + if (thickness == 1) + edge = BDR_RAISEDINNER; + else + edge = EDGE_RAISED; + } - if (shadow_thickness < 0) - shadow_thickness = -shadow_thickness; + if (edges & EDGE_TOP) + border |= BF_TOP; + if (edges & EDGE_LEFT) + border |= BF_LEFT; + if (edges & EDGE_BOTTOM) + border |= BF_BOTTOM; + if (edges & EDGE_RIGHT) + border |= BF_RIGHT; { RECT rect = { x, y, x + width, y + height }; Lisp_Object color = WINDOW_FACE_CACHEL_BACKGROUND (w, findex); mswindows_update_dc (FRAME_MSWINDOWS_DC (f), Qnil, Qnil, color, Qnil); - DrawEdge (FRAME_MSWINDOWS_DC (f), &rect, edge, BF_RECT); + DrawEdge (FRAME_MSWINDOWS_DC (f), &rect, edge, border); } } @@ -1141,7 +1067,7 @@ if (Dynarr_length (buf)) { mswindows_output_string (w, dl, buf, xpos, 0, start_pixpos, width, - findex); + findex, 0, 0, 0, 0); xpos = rb->xpos; width = 0; } @@ -1175,10 +1101,9 @@ else if (rb->object.chr.ch == '\n') { /* Clear in case a cursor was formerly here. */ - int height = DISPLAY_LINE_HEIGHT (dl); - - redisplay_clear_region (window, findex, xpos, dl->ypos - dl->ascent, - rb->width, height); + redisplay_clear_region (window, findex, xpos, + DISPLAY_LINE_YPOS (dl), + rb->width, DISPLAY_LINE_HEIGHT (dl)); elt++; } } @@ -1214,6 +1139,11 @@ else if (rb->type == RUNE_DGLYPH) { Lisp_Object instance; + struct display_box db; + struct display_glyph_area dga; + redisplay_calculate_display_boxes (dl, rb->xpos, rb->object.dglyph.xoffset, + start_pixpos, rb->width, + &db, &dga); XSETWINDOW (window, w); instance = glyph_image_instance (rb->object.dglyph.glyph, @@ -1238,17 +1168,17 @@ else /* #### redisplay-x passes -1 as the width: why ? */ mswindows_output_string (w, dl, buf, xpos, rb->object.dglyph.xoffset, - start_pixpos, rb->width, findex); + start_pixpos, rb->width, findex, + 0, 0, 0, 0); Dynarr_reset (buf); } break; case IMAGE_MONO_PIXMAP: case IMAGE_COLOR_PIXMAP: - mswindows_output_pixmap (w, dl, instance, xpos, - rb->object.dglyph.xoffset, start_pixpos, - rb->width, findex, cursor_start, - cursor_width, cursor_height, 0); + redisplay_output_pixmap (w, instance, &db, &dga, findex, + cursor_start, cursor_width, + cursor_height, 0); if (rb->cursor_type == CURSOR_ON) mswindows_output_cursor (w, dl, xpos, cursor_width, findex, 0, 1); @@ -1259,10 +1189,18 @@ case IMAGE_SUBWINDOW: case IMAGE_WIDGET: - redisplay_output_subwindow (w, dl, instance, xpos, - rb->object.dglyph.xoffset, start_pixpos, - rb->width, findex, cursor_start, - cursor_width, cursor_height); + redisplay_output_subwindow (w, instance, &db, &dga, findex, + cursor_start, cursor_width, + cursor_height); + if (rb->cursor_type == CURSOR_ON) + mswindows_output_cursor (w, dl, xpos, cursor_width, + findex, 0, 1); + break; + + case IMAGE_LAYOUT: + redisplay_output_layout (w, instance, &db, &dga, findex, + cursor_start, cursor_width, + cursor_height); if (rb->cursor_type == CURSOR_ON) mswindows_output_cursor (w, dl, xpos, cursor_width, findex, 0, 1); @@ -1285,7 +1223,8 @@ } if (Dynarr_length (buf)) - mswindows_output_string (w, dl, buf, xpos, 0, start_pixpos, width, findex); + mswindows_output_string (w, dl, buf, xpos, 0, start_pixpos, width, findex, + 0, 0, 0, 0); if (dl->modeline && !EQ (Qzero, w->modeline_shadow_thickness) @@ -1400,12 +1339,11 @@ if (!NILP (background_pixmap)) { + struct display_box db = { x, y, width, height }; mswindows_update_dc (FRAME_MSWINDOWS_DC (f), Qnil, fcolor, bcolor, background_pixmap); - mswindows_output_dibitmap_region - ( f, XIMAGE_INSTANCE (background_pixmap), - x, y, 0, 0, 0, 0, width, height, 0, TRUE); + ( f, XIMAGE_INSTANCE (background_pixmap), &db, 0); } else { @@ -1449,4 +1387,6 @@ CONSOLE_HAS_METHOD (mswindows, flash); CONSOLE_HAS_METHOD (mswindows, ring_bell); CONSOLE_HAS_METHOD (mswindows, bevel_area); + CONSOLE_HAS_METHOD (mswindows, output_string); + CONSOLE_HAS_METHOD (mswindows, output_pixmap); } diff -r 28d9c139be4c -r 11054d720c21 src/redisplay-output.c --- a/src/redisplay-output.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/redisplay-output.c Mon Aug 13 11:26:11 2007 +0200 @@ -2,6 +2,7 @@ Copyright (C) 1994, 1995 Board of Trustees, University of Illinois. Copyright (C) 1995, 1996 Ben Wing. Copyright (C) 1996 Chuck Thompson. + Copyright (C) 1999 Andy Piper. This file is part of XEmacs. @@ -26,6 +27,9 @@ /* Author: Chuck Thompson */ +/* Heavily hacked for modularity, gutter and subwindow support by Andy + Piper. */ + #include #include "lisp.h" @@ -45,6 +49,15 @@ int block, int start, int end, int start_pixpos, int cursor_start, int cursor_width, int cursor_height); +static void redisplay_normalize_display_box (struct display_box* dest, + struct display_glyph_area* src); +static int redisplay_display_boxes_in_window_p (struct window* w, + struct display_box* db, + struct display_glyph_area* dga); +static void redisplay_clear_clipped_region (Lisp_Object locale, face_index findex, + struct display_box* dest, + struct display_glyph_area* glyphsrc, + int fullheight_p, Lisp_Object); /***************************************************************************** sync_rune_structs @@ -191,15 +204,28 @@ else if (crb->type == RUNE_CHAR && (crb->object.chr.ch != drb->object.chr.ch)) return 0; - else if (crb->type == RUNE_DGLYPH && + else if (crb->type == RUNE_HLINE && + (crb->object.hline.thickness != drb->object.hline.thickness || + crb->object.hline.yoffset != drb->object.hline.yoffset)) + return 0; + else if (crb->type == RUNE_DGLYPH && (!EQ (crb->object.dglyph.glyph, drb->object.dglyph.glyph) || !EQ (crb->object.dglyph.extent, drb->object.dglyph.extent) || crb->object.dglyph.xoffset != drb->object.dglyph.xoffset)) return 0; - else if (crb->type == RUNE_HLINE && - (crb->object.hline.thickness != drb->object.hline.thickness || - crb->object.hline.yoffset != drb->object.hline.yoffset)) - return 0; + /* Only check dirtiness if we know something has changed. */ + else if (crb->type == RUNE_DGLYPH && + XFRAME (w->frame)->glyphs_changed) + { + glyph_index gindex = get_glyph_cachel_index (w, drb->object.dglyph.glyph); + /* Although doing the cachel lookup for every comparison is + very expensive.we have to do it to make sure the cache is + up-to-date. */ + if (GLYPH_CACHEL_DIRTYP (w, gindex)) + return 0; + else + return 1; + } else return 1; } @@ -351,8 +377,14 @@ force = 1; if (f->windows_structure_changed || + /* #### Why is this so? We have face cachels so that we don't + have to recalculate all the display blocks when faces + change. I have fixed this for glyphs and am inclined to think + that faces should "Just Work", but I'm not feeling brave + today. Maybe its because the face cachels represent merged + faces rather than simply instantiations in a particular + domain. */ f->faces_changed || - f->glyphs_changed || cdl->ypos != ddl->ypos || cdl->ascent != ddl->ascent || cdl->descent != ddl->descent || @@ -589,6 +621,7 @@ (cdl && (cdl->ypos != ddl->ypos || cdl->ascent != ddl->ascent || cdl->descent != ddl->descent || + cdl->top_clip != ddl->top_clip || cdl->clip != ddl->clip))) { int x, y, width, height; @@ -596,9 +629,9 @@ must_sync = 1; x = start_pixpos; - y = ddl->ypos - ddl->ascent; + y = DISPLAY_LINE_YPOS (ddl); width = min (next_start_pixpos, block_end) - x; - height = ddl->ascent + ddl->descent - ddl->clip; + height = DISPLAY_LINE_HEIGHT (ddl); if (x < ddl->bounds.left_in) { @@ -658,7 +691,11 @@ region or if it was a block of a different type, then output the entire ddb. Otherwise, compare cdb and ddb and output only the changed region. */ - if (!force && cdb && ddb->type == cdb->type && b == old_b) + if (!force && cdb && ddb->type == cdb->type + /* If there was no buffer being display before the + compare anyway as we might be outputting a gutter. */ + && + (b == old_b || !old_b)) { must_sync |= compare_display_blocks (w, cdl, ddl, old_block, block, start_pixpos, @@ -709,19 +746,23 @@ if (f->windows_structure_changed || f->faces_changed || clear_border || f->clear) { - int y = ddl->ypos - ddl->ascent; - int height = ddl->ascent + ddl->descent - ddl->clip; + int y = DISPLAY_LINE_YPOS (ddl); + int height = DISPLAY_LINE_HEIGHT (ddl); - if (ddl->modeline) + /* If we are in the gutter then we musn't clear the borders. */ + if (y >= WINDOW_TEXT_TOP (w) && (y + height) <= WINDOW_TEXT_BOTTOM (w)) { - y -= MODELINE_SHADOW_THICKNESS (w); - height += (2 * MODELINE_SHADOW_THICKNESS (w)); + if (ddl->modeline) + { + y -= MODELINE_SHADOW_THICKNESS (w); + height += (2 * MODELINE_SHADOW_THICKNESS (w)); + } + + if (window_is_leftmost (w)) + clear_left_border (w, y, height); + if (window_is_rightmost (w)) + clear_right_border (w, y, height); } - - if (window_is_leftmost (w)) - clear_left_border (w, y, height); - if (window_is_rightmost (w)) - clear_right_border (w, y, height); } if (cdla) @@ -1005,20 +1046,38 @@ { struct frame *f = XFRAME (w->frame); struct device *d = XDEVICE (f->device); + struct display_block *db = Dynarr_atp (dl->display_blocks, block); + rune_dynarr *rba = db->runes; + struct rune *rb; + int xpos, width; + rb = Dynarr_atp (rba, start); + if (!rb) + /* Nothing to do so don't do anything. */ + return; + + xpos = max (start_pixpos, rb->xpos); + + if (end < 0) + end = Dynarr_length (rba); + + rb = Dynarr_atp (rba, end - 1); + width = rb->xpos + rb->width - xpos; + /* now actually output the block. */ DEVMETH (d, output_display_block, (w, dl, block, start, end, start_pixpos, cursor_start, cursor_width, cursor_height)); } - + /**************************************************************************** redisplay_unmap_subwindows Remove subwindows from the area in the box defined by the given parameters. ****************************************************************************/ -static void redisplay_unmap_subwindows (struct frame* f, int x, int y, int width, int height) +static void redisplay_unmap_subwindows (struct frame* f, int x, int y, int width, int height, + Lisp_Object ignored_window) { int elt; @@ -1031,7 +1090,9 @@ && cachel->x + cachel->width > x && cachel->x < x + width && - cachel->y + cachel->height > y && cachel->y < y + height) + cachel->y + cachel->height > y && cachel->y < y + height + && + !EQ (cachel->subwindow, ignored_window)) { unmap_subwindow (cachel->subwindow); } @@ -1048,79 +1109,340 @@ { if (Dynarr_length (FRAME_SUBWINDOW_CACHE (f))) { - redisplay_unmap_subwindows (f, x, y, width, height); + redisplay_unmap_subwindows (f, x, y, width, height, Qnil); + } +} + +static void redisplay_unmap_subwindows_except_us (struct frame* f, int x, int y, int width, + int height, Lisp_Object subwindow) +{ + if (Dynarr_length (FRAME_SUBWINDOW_CACHE (f))) + { + redisplay_unmap_subwindows (f, x, y, width, height, subwindow); } } /**************************************************************************** redisplay_output_subwindow - output a subwindow. This code borrows heavily from the pixmap stuff, although is much simpler not needing to account for partial pixmaps, backgrounds etc. ****************************************************************************/ void -redisplay_output_subwindow (struct window *w, struct display_line *dl, - Lisp_Object image_instance, int xpos, int xoffset, - int start_pixpos, int width, face_index findex, - int cursor_start, int cursor_width, int cursor_height) +redisplay_output_subwindow (struct window *w, + Lisp_Object image_instance, + struct display_box* db, struct display_glyph_area* dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height) { struct Lisp_Image_Instance *p = XIMAGE_INSTANCE (image_instance); Lisp_Object window; + struct display_glyph_area sdga; - int lheight = dl->ascent + dl->descent - dl->clip; - int pheight = ((int) IMAGE_INSTANCE_SUBWINDOW_HEIGHT (p) > lheight ? lheight : - IMAGE_INSTANCE_SUBWINDOW_HEIGHT (p)); + dga->height = IMAGE_INSTANCE_SUBWINDOW_HEIGHT (p); + dga->width = IMAGE_INSTANCE_SUBWINDOW_WIDTH (p); + + /* This makes the glyph area fit into the display area. */ + if (!redisplay_normalize_glyph_area (db, dga)) + return; + + XSETWINDOW (window, w); + + /* Clear the area the subwindow is going into. */ + redisplay_clear_clipped_region (window, findex, + db, dga, 0, image_instance); + + /* This shrinks the display box to exactly enclose the glyph + area. */ + redisplay_normalize_display_box (db, dga); + + /* if we can't view the whole window we can't view any of it. We + have to be careful here since we may be being asked to display + part of a subwindow, the rest of which is on-screen as well. We + need to allow this case and map the entire subwindow. We also + need to be careful since the subwindow could be outside the + window in the gutter or modeline - we also need to allow these + cases.*/ + sdga.xoffset = -dga->xoffset; + sdga.yoffset = -dga->yoffset; + sdga.height = IMAGE_INSTANCE_SUBWINDOW_HEIGHT (p); + sdga.width = IMAGE_INSTANCE_SUBWINDOW_WIDTH (p); + + if (redisplay_display_boxes_in_window_p (w, db, &sdga) < 0) + { + map_subwindow (image_instance, db->xpos, db->ypos, dga); + } + else + { + sdga.xoffset = sdga.yoffset = 0; + map_subwindow (image_instance, db->xpos - dga->xoffset, + db->ypos - dga->yoffset, &sdga); + } +} + +/**************************************************************************** + redisplay_output_layout + + Output a widget hierarchy. This can safely call itself recursively. + ****************************************************************************/ +void +redisplay_output_layout (struct window *w, + Lisp_Object image_instance, + struct display_box* db, struct display_glyph_area* dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height) +{ + struct Lisp_Image_Instance *p = XIMAGE_INSTANCE (image_instance); + Lisp_Object window, rest; + Emchar_dynarr *buf = Dynarr_new (Emchar); + struct frame *f = XFRAME (w->frame); + struct device *d = XDEVICE (f->device); + int layout_height, layout_width; + /* We bogusly don't take f->extents_changed and f->glyphs_changed + into account. This is because if we do we always redisplay the + entire layout. So far I have seen no ill effects to we'll see. */ + int frame_changed = (f->buffers_changed || + f->clip_changed || + f->faces_changed || + f->frame_changed || + f->modeline_changed || + f->subwindows_changed || + f->windows_changed || + f->windows_structure_changed); XSETWINDOW (window, w); - /* Clear the area the subwindow is going into. The subwindow itself - will always take care of the full width. We don't want to clear - where it is going to go in order to avoid flicker. So, all we - have to take care of is any area above or below the subwindow. Of - course this is rubbish if the subwindow has transparent areas - (for instance with frames). */ - /* #### We take a shortcut for now. We know that since we have - subwindow_offset hardwired to 0 that the subwindow is against the top - edge so all we have to worry about is below it. */ - if ((int) (dl->ypos - dl->ascent + pheight) < - (int) (dl->ypos + dl->descent - dl->clip)) + layout_height = glyph_height (image_instance, Qnil, findex, window); + layout_width = glyph_width (image_instance, Qnil, findex, window); + + dga->height = layout_height; + dga->width = layout_width; + + /* This makes the glyph area fit into the display area. */ + if (!redisplay_normalize_glyph_area (db, dga)) + return; + + /* Highly dodgy optimization. We want to only output the whole + layout if we really have to. */ + if (frame_changed || IMAGE_INSTANCE_DIRTYP (p)) { - int clear_x, clear_width; - - int clear_y = dl->ypos - dl->ascent + pheight; - int clear_height = lheight - pheight; + /* First clear the area we are drawing into. This is the easiest + thing to do since we have many gaps that we have to make sure are + filled in. */ + redisplay_clear_clipped_region (window, findex, db, dga, 1, Qnil); + + /* Output a border if required */ + if (!NILP (IMAGE_INSTANCE_LAYOUT_BORDER (p))) + { + int edges = 0; + enum edge_style style; + int ypos = db->ypos; + int height = dga->height; + + if (dga->xoffset >= 0) + edges |= EDGE_LEFT; + if (dga->width - dga->xoffset == layout_width) + edges |= EDGE_RIGHT; + if (dga->yoffset >= 0) + edges |= EDGE_TOP; + if (dga->height - dga->yoffset == layout_height) + edges |= EDGE_BOTTOM; + + if (EQ (IMAGE_INSTANCE_LAYOUT_BORDER (p), Qetched_in)) + style = EDGE_ETCHED_IN; + else if (EQ (IMAGE_INSTANCE_LAYOUT_BORDER (p), Qetched_out)) + style = EDGE_ETCHED_OUT; + else if (EQ (IMAGE_INSTANCE_LAYOUT_BORDER (p), Qbevel_in)) + style = EDGE_BEVEL_IN; + else if (INTP (IMAGE_INSTANCE_LAYOUT_BORDER (p))) + { + style = EDGE_ETCHED_IN; + if (edges & EDGE_TOP) + { + ypos += XINT (IMAGE_INSTANCE_LAYOUT_BORDER (p)); + height -= XINT (IMAGE_INSTANCE_LAYOUT_BORDER (p)); + } + } + else + style = EDGE_BEVEL_OUT; - if (start_pixpos >= 0 && start_pixpos > xpos) - { - clear_x = start_pixpos; - clear_width = xpos + width - start_pixpos; + MAYBE_DEVMETH (d, bevel_area, + (w, findex, db->xpos, + ypos, + dga->width, height, 2, edges, style)); } - else - { - clear_x = xpos; - clear_width = width; - } - - redisplay_clear_region (window, findex, clear_x, clear_y, - clear_width, clear_height); } -#if 0 - redisplay_clear_region (window, findex, xpos - xoffset, dl->ypos - dl->ascent, - width, lheight); -#endif - /* if we can't view the whole window we can't view any of it */ - if (IMAGE_INSTANCE_SUBWINDOW_HEIGHT (p) > lheight - || - IMAGE_INSTANCE_SUBWINDOW_WIDTH (p) > width) + + /* This shrinks the display box to exactly enclose the glyph + area. */ + redisplay_normalize_display_box (db, dga); + + /* Flip through the widgets in the layout displaying as necessary */ + LIST_LOOP (rest, IMAGE_INSTANCE_LAYOUT_CHILDREN (p)) { - redisplay_clear_region (window, findex, xpos - xoffset, dl->ypos - dl->ascent, - width, lheight); - unmap_subwindow (image_instance); + Lisp_Object child = XCAR (rest); + + struct display_box cdb; + /* For losing HP-UX */ + cdb.xpos = db->xpos; + cdb.ypos = db->ypos; + cdb.width = db->width; + cdb.height = db->height; + + /* First determine if the image is visible at all */ + if (IMAGE_INSTANCEP (child)) + { + struct Lisp_Image_Instance* childii = XIMAGE_INSTANCE (child); + /* The enclosing layout offsets are +ve at this point */ + struct display_glyph_area cdga; + cdga.xoffset = IMAGE_INSTANCE_XOFFSET (childii) - dga->xoffset; + cdga.yoffset = IMAGE_INSTANCE_YOFFSET (childii) - dga->yoffset; + cdga.width = glyph_width (child, Qnil, findex, window); + cdga.height = glyph_height (child, Qnil, findex, window); + + /* Although normalization is done by the output routines + we have to do it here so that they don't try and + clear all of db. This is true below also. */ + if (redisplay_normalize_glyph_area (&cdb, &cdga)) + { + redisplay_normalize_display_box (&cdb, &cdga); + /* Since the display boxes will now be totally in the + window if they are visible at all we can now check this easily. */ + if (cdb.xpos < db->xpos || cdb.ypos < db->ypos + || cdb.xpos + cdb.width > db->xpos + db->width + || cdb.ypos + cdb.height > db->ypos + db->height) + continue; + /* We have to invert the offset here as normalization + will have made them positive which the output + routines will treat as a truely +ve offset. */ + cdga.xoffset = -cdga.xoffset; + cdga.yoffset = -cdga.yoffset; + + switch (IMAGE_INSTANCE_TYPE (childii)) + { + case IMAGE_TEXT: + { + /* #### This is well hacked and could use some + generalisation.*/ + if (redisplay_normalize_glyph_area (&cdb, &cdga) + && + (frame_changed || IMAGE_INSTANCE_DIRTYP (childii))) + { + struct display_line dl; /* this is fake */ + Lisp_Object string = + IMAGE_INSTANCE_TEXT_STRING (childii); + convert_bufbyte_string_into_emchar_dynarr + (XSTRING_DATA (string), XSTRING_LENGTH (string), buf); + + redisplay_normalize_display_box (&cdb, &cdga); + /* Offsets are now +ve again so be careful + when fixing up the display line. */ + xzero (dl); + /* Munge boxes into display lines. */ + dl.ypos = (cdb.ypos - cdga.yoffset) + + glyph_ascent (child, Qnil, findex, window); + dl.ascent = glyph_ascent (child, Qnil, findex, window); + dl.descent = glyph_descent (child, Qnil, findex, window); + dl.top_clip = cdga.yoffset; + dl.clip = (dl.ypos + dl.descent) - (cdb.ypos + cdb.height); + /* output_string doesn't understand offsets in + the same way as other routines - we have to + add the offset to the width so that we + output the full string. */ + MAYBE_DEVMETH (d, output_string, (w, &dl, buf, cdb.xpos, + cdga.xoffset, cdb.xpos, + cdga.width + cdga.xoffset, + findex, 0, 0, 0, 0)); + Dynarr_reset (buf); + } + } + break; + + case IMAGE_MONO_PIXMAP: + case IMAGE_COLOR_PIXMAP: + if (frame_changed || IMAGE_INSTANCE_DIRTYP (childii)) + redisplay_output_pixmap (w, child, &cdb, &cdga, findex, + 0, 0, 0, 0); + break; + + case IMAGE_WIDGET: + case IMAGE_SUBWINDOW: + if (frame_changed || IMAGE_INSTANCE_DIRTYP (childii)) + redisplay_output_subwindow (w, child, &cdb, &cdga, findex, + 0, 0, 0); + break; + + case IMAGE_LAYOUT: + redisplay_output_layout (w, child, &cdb, &cdga, findex, + 0, 0, 0); + break; + + case IMAGE_NOTHING: + /* nothing is as nothing does */ + break; + + case IMAGE_POINTER: + default: + abort (); + } + } + } } - else - map_subwindow (image_instance, xpos - xoffset, dl->ypos - dl->ascent); + Dynarr_free (buf); +} + +/**************************************************************************** + redisplay_output_pixmap + + + output a pixmap. + ****************************************************************************/ +void +redisplay_output_pixmap (struct window *w, + Lisp_Object image_instance, + struct display_box* db, struct display_glyph_area* dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height, int offset_bitmap) +{ + struct frame *f = XFRAME (w->frame); + struct device *d = XDEVICE (f->device); + struct Lisp_Image_Instance *p = XIMAGE_INSTANCE (image_instance); + Lisp_Object window; + XSETWINDOW (window, w); + + dga->height = IMAGE_INSTANCE_PIXMAP_HEIGHT (p); + dga->width = IMAGE_INSTANCE_PIXMAP_WIDTH (p); + + /* This makes the glyph area fit into the display area. */ + if (!redisplay_normalize_glyph_area (db, dga)) + return; + + /* Clear the area the pixmap is going into. The pixmap itself will + always take care of the full width. We don't want to clear where + it is going to go in order to avoid flicker. So, all we have to + take care of is any area above or below the pixmap. If the pixmap + has a mask in which case we have to clear the whole damn thing + since we can't yet clear just the area not included in the + mask. */ + if (!offset_bitmap) + { + redisplay_clear_clipped_region (window, findex, + db, dga, + (int)IMAGE_INSTANCE_PIXMAP_MASK (p), + Qnil); + + /* This shrinks the display box to exactly enclose the glyph + area. */ + redisplay_normalize_display_box (db, dga); + } + assert (db->xpos >= 0 && db->ypos >= 0); + + MAYBE_DEVMETH (d, output_pixmap, (w, image_instance, + db, dga, + findex, cursor_start, + cursor_width, cursor_height, + offset_bitmap)); } /**************************************************************************** @@ -1159,10 +1481,7 @@ d = XDEVICE (f->device); /* if we have subwindows in the region we have to unmap them */ - if (Dynarr_length (FRAME_SUBWINDOW_CACHE (f))) - { - redisplay_unmap_subwindows (f, x, y, width, height); - } + redisplay_unmap_subwindows_maybe (f, x, y, width, height); /* #### This isn't quite right for when this function is called from the toolbar code. */ @@ -1228,6 +1547,224 @@ (locale, d, f, findex, x, y, width, height, fcolor, bcolor, background_pixmap)); } +/**************************************************************************** + redisplay_clear_clipped_region + + Clear the area in the dest display_box not covered by the src + display_glyph_area using the given face. This is a common occurance + for images shorter than the display line. Clipping can be played + around with by altering these. glyphsrc should be normalized. + ****************************************************************************/ +static void +redisplay_clear_clipped_region (Lisp_Object window, face_index findex, + struct display_box* dest, struct display_glyph_area* glyphsrc, + int fullheight_p, Lisp_Object ignored_subwindow) +{ + /* assume dest->xpos >= 0 */ + int clear_x; + struct frame* f = XFRAME (XWINDOW (window)->frame); + + if (glyphsrc->xoffset > 0) + { + clear_x = dest->xpos + glyphsrc->xoffset; + } + else + { + clear_x = dest->xpos; + } + + /* If we need the whole height cleared then just do it. */ + if (fullheight_p) + { + redisplay_clear_region (window, findex, clear_x, dest->ypos, + glyphsrc->width, dest->height); + } + else + { + int yoffset = (glyphsrc->yoffset > 0 ? glyphsrc->yoffset : 0); + + /* We need to make sure that subwindows are unmapped from the + whole area. */ + redisplay_unmap_subwindows_except_us (f, clear_x, dest->ypos, + glyphsrc->width, dest->height, + ignored_subwindow); + /* first the top box */ + if (yoffset > 0) + { + redisplay_clear_region (window, findex, clear_x, dest->ypos, + glyphsrc->width, yoffset); + + } + /* Then the bottom box */ + if (yoffset + glyphsrc->height < dest->height) + { + redisplay_clear_region (window, findex, clear_x, + dest->ypos + yoffset + glyphsrc->height, + glyphsrc->width, + dest->height - (yoffset + glyphsrc->height)); + + } + } +} + +/***************************************************************************** + redisplay_normalize_glyph_area + redisplay_normalize_display_box + + Calculate the visible box for displaying src in dest. + ****************************************************************************/ +int +redisplay_normalize_glyph_area (struct display_box* dest, + struct display_glyph_area* glyphsrc) +{ + if (dest->xpos + glyphsrc->xoffset > dest->xpos + dest->width + || + dest->ypos + glyphsrc->yoffset > dest->ypos + dest->height + || + -glyphsrc->xoffset >= glyphsrc->width + || + -glyphsrc->yoffset >= glyphsrc->height) + { + /* It's all clipped out */ + return 0; + } + + /* Horizontal offsets. This works because xoffset can be -ve as well as +ve */ + if (dest->xpos + glyphsrc->xoffset + glyphsrc->width > dest->xpos + dest->width) + { + if (glyphsrc->xoffset > 0) + glyphsrc->width = dest->width - glyphsrc->xoffset; + else + glyphsrc->width = dest->width; + } + + if (glyphsrc->xoffset < 0) + glyphsrc->width += glyphsrc->xoffset; + + /* Vertical offsets. This works because yoffset can be -ve as well as +ve */ + if (dest->ypos + glyphsrc->yoffset + glyphsrc->height > dest->ypos + dest->height) + { + if (glyphsrc->yoffset > 0) + glyphsrc->height = dest->height - glyphsrc->yoffset; + else + glyphsrc->height = dest->height; + } + + if (glyphsrc->yoffset < 0) + glyphsrc->height += glyphsrc->yoffset; + + return 1; +} + +static void +redisplay_normalize_display_box (struct display_box* dest, + struct display_glyph_area* glyphsrc) +{ + /* Adjust the destination area. At the end of this the destination + area will exactly enclose the glyph area. The only remaining + adjustment will be offsets into the glyph area. */ + + /* Horizontal adjustment. */ + if (glyphsrc->xoffset > 0) + { + dest->xpos += glyphsrc->xoffset; + dest->width -= glyphsrc->xoffset; + glyphsrc->xoffset = 0; + } + else + glyphsrc->xoffset = -glyphsrc->xoffset; + + if (glyphsrc->width < dest->width) + dest->width = glyphsrc->width; + + /* Vertical adjustment. */ + if (glyphsrc->yoffset > 0) + { + dest->ypos += glyphsrc->yoffset; + dest->height -= glyphsrc->yoffset; + glyphsrc->yoffset = 0; + } + else + glyphsrc->yoffset = -glyphsrc->yoffset; + + if (glyphsrc->height < dest->height) + dest->height = glyphsrc->height; +} + +/***************************************************************************** + redisplay_display_boxes_in_window_p + + Determine whether the require display_glyph_area is completely inside + the window. 0 means the display_box is not in the window. 1 means the + display_box and the display_glyph_area are in the window. -1 means + the display_box is in the window but the display_glyph_area is not. + ****************************************************************************/ +static int +redisplay_display_boxes_in_window_p (struct window* w, + struct display_box* db, + struct display_glyph_area* dga) +{ + int left = WINDOW_TEXT_LEFT (w); + int right = WINDOW_TEXT_RIGHT (w); + int top = WINDOW_TEXT_TOP (w); + int bottom = WINDOW_TEXT_BOTTOM (w); + + if (db->xpos < left || db->ypos < top + || db->xpos + db->width > right + || db->ypos + db->height > bottom) + /* We are not displaying in a window at all */ + return 0; + + if (db->xpos + dga->xoffset >= left + && + db->ypos + dga->yoffset >= top + && + db->xpos + dga->xoffset + dga->width <= right + && + db->ypos + dga->yoffset + dga->height <= bottom) + return 1; + + return -1; +} + +/***************************************************************************** + redisplay_calculate_display_boxes + + Convert from rune/display_line co-ordinates to display_box + co-ordinates. + ****************************************************************************/ +int +redisplay_calculate_display_boxes (struct display_line *dl, int xpos, + int xoffset, int start_pixpos, int width, + struct display_box* dest, + struct display_glyph_area* src) +{ + dest->xpos = xpos; + dest->ypos = DISPLAY_LINE_YPOS (dl); + dest->width = width; + dest->height = DISPLAY_LINE_HEIGHT (dl); + + src->xoffset = -xoffset; + src->yoffset = -dl->top_clip; + src->width = 0; + src->height = 0; + + if (start_pixpos >=0 && start_pixpos > xpos) + { + /* Oops, we're asking for a start outside of the displayable + area. */ + if (start_pixpos > xpos + width) + return 0; + dest->xpos = start_pixpos; + dest->width -= (start_pixpos - xpos); + /* Offsets are -ve when we want to clip pixels off the displayed + glyph. */ + src->xoffset -= (start_pixpos - xpos); + } + + return 1; +} + /***************************************************************************** redisplay_clear_top_of_window @@ -1283,7 +1820,6 @@ if (height) { - struct frame *f = XFRAME (w->frame); Lisp_Object window; int bflag = 0 ; /* (window_needs_vertical_divider (w) ? 0 : 1);*/ layout_bounds bounds; @@ -1332,7 +1868,6 @@ int min_start, int max_end) { struct frame *f = XFRAME (w->frame); - struct device *d = XDEVICE (f->device); int ypos1, ypos2; int ddla_len = Dynarr_length (ddla); @@ -1684,6 +2219,7 @@ struct device *d = XDEVICE (f->device); int x, y, width, height; int shadow_thickness = MODELINE_SHADOW_THICKNESS (w); + enum edge_style style; x = WINDOW_MODELINE_LEFT (w); width = WINDOW_MODELINE_RIGHT (w) - x; @@ -1691,8 +2227,15 @@ height = dl->ascent + dl->descent + 2 * shadow_thickness; if (XINT (w->modeline_shadow_thickness) < 0) - shadow_thickness = - shadow_thickness; + { + style = EDGE_BEVEL_IN; + } + else + { + style = EDGE_BEVEL_OUT; + } MAYBE_DEVMETH (d, bevel_area, - (w, MODELINE_INDEX, x, y, width, height, shadow_thickness)); + (w, MODELINE_INDEX, x, y, width, height, shadow_thickness, + EDGE_ALL, style)); } diff -r 28d9c139be4c -r 11054d720c21 src/redisplay-tty.c --- a/src/redisplay-tty.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/redisplay-tty.c Mon Aug 13 11:26:11 2007 +0200 @@ -392,6 +392,7 @@ case IMAGE_COLOR_PIXMAP: case IMAGE_SUBWINDOW: case IMAGE_WIDGET: + case IMAGE_LAYOUT: /* just do nothing here */ break; @@ -464,7 +465,7 @@ static void tty_clear_region (Lisp_Object window, struct device* d, struct frame * f, face_index findex, int x, int y, - int width, int height, Lisp_Object fcolor, Lisp_Object bcolor, + int width, int height, Lisp_Object fcolor, Lisp_Object bcolor, Lisp_Object background_pixmap) { struct console *c = XCONSOLE (FRAME_CONSOLE (f)); @@ -949,11 +950,11 @@ { Lisp_Object dev = CONSOLE_SELECTED_DEVICE (c); - if (!GC_NILP (dev)) + if (!NILP (dev)) { Lisp_Object frm = DEVICE_SELECTED_FRAME (XDEVICE (dev)); - if (!GC_NILP (frm)) + if (!NILP (frm)) { struct frame *f = XFRAME (frm); @@ -1304,7 +1305,8 @@ struct fkey_table { - CONST char *cap, *name; + CONST char *cap; + CONST char *name; }; /* Termcap capability names that correspond directly to X keysyms. @@ -1444,22 +1446,18 @@ describes F10, whereas othertimes it describes F0 and "k;" describes F10. We will attempt to politely accommodate both systems by testing for "k;", and if it is present, assuming that "k0" denotes F0, otherwise F10. - */ + */ { - char *k_semi = tgetstr ("k;", address); - char *k0 = tgetstr ("k0", address); - CONST char *k0_name = "f10"; + CONST char *k_semi = tgetstr ("k;", address); + CONST char *k0 = tgetstr ("k0", address); if (k_semi) - { - Fdefine_key (function_key_map, build_ext_string (k_semi, FORMAT_BINARY), - vector1 (intern ("f10"))); - k0_name = "f0"; - } + Fdefine_key (function_key_map, build_ext_string (k_semi, FORMAT_BINARY), + vector1 (intern ("f10"))); if (k0) Fdefine_key (function_key_map, build_ext_string (k0, FORMAT_BINARY), - vector1 (intern (k0_name))); + vector1 (intern (k_semi ? "f0" : "f10"))); } /* Set up cookies for numbered function keys above f10. */ @@ -1487,42 +1485,40 @@ } } } - } + } /* * Various mappings to try and get a better fit. */ - { -#define CONDITIONAL_REASSIGN(cap1, cap2, sym) \ - if (!tgetstr (cap1, address)) \ - { \ - char *sequence = tgetstr (cap2, address); \ - if (sequence) \ - Fdefine_key (function_key_map, \ - build_ext_string (sequence, FORMAT_BINARY), \ - vector1 (intern (sym))); \ - } +#define CONDITIONAL_REASSIGN(cap1, cap2, keyname) \ + if (!tgetstr (cap1, address)) \ + { \ + char *sequence = tgetstr (cap2, address); \ + if (sequence) \ + Fdefine_key (function_key_map, \ + build_ext_string (sequence, FORMAT_BINARY), \ + vector1 (intern (keyname))); \ + } - /* if there's no key_next keycap, map key_npage to `next' keysym */ - CONDITIONAL_REASSIGN ("%5", "kN", "next"); - /* if there's no key_prev keycap, map key_ppage to `previous' keysym */ - CONDITIONAL_REASSIGN ("%8", "kP", "prior"); - /* if there's no key_dc keycap, map key_ic to `insert' keysym */ - CONDITIONAL_REASSIGN ("kD", "kI", "insert"); + /* if there's no key_next keycap, map key_npage to `next' keysym */ + CONDITIONAL_REASSIGN ("%5", "kN", "next"); + /* if there's no key_prev keycap, map key_ppage to `previous' keysym */ + CONDITIONAL_REASSIGN ("%8", "kP", "prior"); + /* if there's no key_dc keycap, map key_ic to `insert' keysym */ + CONDITIONAL_REASSIGN ("kD", "kI", "insert"); - /* IBM has their own non-standard dialect of terminfo. - If the standard name isn't found, try the IBM name. */ - CONDITIONAL_REASSIGN ("kB", "KO", "backtab"); - CONDITIONAL_REASSIGN ("@4", "kJ", "execute"); /* actually "action" */ - CONDITIONAL_REASSIGN ("@4", "kc", "execute"); /* actually "command" */ - CONDITIONAL_REASSIGN ("%7", "ki", "menu"); - CONDITIONAL_REASSIGN ("@7", "kw", "end"); - CONDITIONAL_REASSIGN ("F1", "k<", "f11"); - CONDITIONAL_REASSIGN ("F2", "k>", "f12"); - CONDITIONAL_REASSIGN ("%1", "kq", "help"); - CONDITIONAL_REASSIGN ("*6", "kU", "select"); + /* IBM has their own non-standard dialect of terminfo. + If the standard name isn't found, try the IBM name. */ + CONDITIONAL_REASSIGN ("kB", "KO", "backtab"); + CONDITIONAL_REASSIGN ("@4", "kJ", "execute"); /* actually "action" */ + CONDITIONAL_REASSIGN ("@4", "kc", "execute"); /* actually "command" */ + CONDITIONAL_REASSIGN ("%7", "ki", "menu"); + CONDITIONAL_REASSIGN ("@7", "kw", "end"); + CONDITIONAL_REASSIGN ("F1", "k<", "f11"); + CONDITIONAL_REASSIGN ("F2", "k>", "f12"); + CONDITIONAL_REASSIGN ("%1", "kq", "help"); + CONDITIONAL_REASSIGN ("*6", "kU", "select"); #undef CONDITIONAL_REASSIGN - } return Qnil; } diff -r 28d9c139be4c -r 11054d720c21 src/redisplay-x.c --- a/src/redisplay-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/redisplay-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -54,17 +54,10 @@ #endif /* Number of pixels below each line. */ -/* #### implement me */ -int x_interline_space; +int x_interline_space; /* #### implement me */ #define EOL_CURSOR_WIDTH 5 -static void x_output_pixmap (struct window *w, struct display_line *dl, - Lisp_Object image_instance, int xpos, - int xoffset, - int start_pixpos, int width, face_index findex, - int cursor_start, int cursor_width, - int cursor_height); static void x_output_vertical_divider (struct window *w, int clear); static void x_output_blank (struct window *w, struct display_line *dl, struct rune *rb, int start_pixpos, @@ -79,7 +72,6 @@ int xpos, face_index findex); static void x_clear_frame (struct frame *f); static void x_clear_frame_windows (Lisp_Object window); -void bevel_modeline (struct window *w, struct display_line *dl); /* Note: We do not use the Xmb*() functions and XFontSets. @@ -408,10 +400,10 @@ else if (rb->object.chr.ch == '\n') { /* Clear in case a cursor was formerly here. */ - int height = dl->ascent + dl->descent - dl->clip; - - redisplay_clear_region (window, findex, xpos, dl->ypos - dl->ascent, - rb->width, height); + redisplay_clear_region (window, findex, xpos, + DISPLAY_LINE_YPOS (dl), + rb->width, + DISPLAY_LINE_HEIGHT (dl)); elt++; } } @@ -445,6 +437,11 @@ else if (rb->type == RUNE_DGLYPH) { Lisp_Object instance; + struct display_box dbox; + struct display_glyph_area dga; + redisplay_calculate_display_boxes (dl, rb->xpos, rb->object.dglyph.xoffset, + start_pixpos, rb->width, + &dbox, &dga); XSETWINDOW (window, w); instance = glyph_image_instance (rb->object.dglyph.glyph, @@ -475,26 +472,29 @@ case IMAGE_MONO_PIXMAP: case IMAGE_COLOR_PIXMAP: - x_output_pixmap (w, dl, instance, xpos, - rb->object.dglyph.xoffset, start_pixpos, - rb->width, findex, cursor_start, - cursor_width, cursor_height); + redisplay_output_pixmap (w, instance, &dbox, &dga, findex, + cursor_start, cursor_width, + cursor_height, 0); break; - case IMAGE_POINTER: - abort (); - case IMAGE_WIDGET: case IMAGE_SUBWINDOW: - redisplay_output_subwindow (w, dl, instance, xpos, - rb->object.dglyph.xoffset, start_pixpos, - rb->width, findex, cursor_start, - cursor_width, cursor_height); + redisplay_output_subwindow (w, instance, &dbox, &dga, findex, + cursor_start, cursor_width, + cursor_height); + break; + + case IMAGE_LAYOUT: + redisplay_output_layout (w, instance, &dbox, &dga, findex, + cursor_start, cursor_width, + cursor_height); + break; case IMAGE_NOTHING: /* nothing is as nothing does */ break; + case IMAGE_POINTER: default: abort (); } @@ -531,7 +531,7 @@ static void x_bevel_area (struct window *w, face_index findex, int x, int y, int width, int height, - int shadow_thickness) + int shadow_thickness, int edges, enum edge_style style) { struct frame *f = XFRAME (w->frame); struct device *d = XDEVICE (f->device); @@ -549,6 +549,7 @@ int flip_gcs = 0; unsigned long mask; + assert (shadow_thickness >=0); memset (&gcv, ~0, sizeof (XGCValues)); tmp_pixel = WINDOW_FACE_CACHEL_BACKGROUND (w, findex); @@ -618,24 +619,33 @@ gcv.foreground = background_pixel; background_gc = gc_cache_lookup (DEVICE_X_GC_CACHE (d), &gcv, mask); - /* possibly revert the GC's in case the shadow thickness is < 0. - This will give a depressed look to the divider */ - if (shadow_thickness < 0) + /* possibly revert the GC's This will give a depressed look to the + divider */ + if (style == EDGE_ETCHED_IN || style == EDGE_BEVEL_IN) { GC temp; temp = top_shadow_gc; top_shadow_gc = bottom_shadow_gc; bottom_shadow_gc = temp; + } - /* better avoid a Bad Address XLib error ;-) */ - shadow_thickness = - shadow_thickness; - } + if (style == EDGE_ETCHED_IN || style == EDGE_ETCHED_OUT) + shadow_thickness /= 2; /* Draw the shadows around the divider line */ x_output_shadows (f, x, y, width, height, top_shadow_gc, bottom_shadow_gc, - background_gc, shadow_thickness); + background_gc, shadow_thickness, edges); + + if (style == EDGE_ETCHED_IN || style == EDGE_ETCHED_OUT) + { + /* Draw the shadows around the divider line */ + x_output_shadows (f, x + shadow_thickness, y + shadow_thickness, + width - 2*shadow_thickness, height - 2*shadow_thickness, + bottom_shadow_gc, top_shadow_gc, + background_gc, shadow_thickness, edges); + } } /***************************************************************************** @@ -803,7 +813,7 @@ if (width < 0) width = x_text_width (f, cachel, Dynarr_atp (buf, 0), Dynarr_length (buf)); - height = dl->ascent + dl->descent - dl->clip; + height = DISPLAY_LINE_HEIGHT (dl); /* Regularize the variables passed in. */ @@ -816,6 +826,10 @@ xpos -= xoffset; + /* make sure the area we are about to display is subwindow free. */ + redisplay_unmap_subwindows_maybe (f, clip_start, DISPLAY_LINE_YPOS (dl), + clip_end - clip_start, DISPLAY_LINE_HEIGHT (dl)); + nruns = separate_textual_runs (text_storage, runs, Dynarr_atp (buf, 0), Dynarr_length (buf)); @@ -860,7 +874,7 @@ if (bgc) XFillRectangle (dpy, x_win, bgc, clip_start, - dl->ypos - dl->ascent, clip_end - clip_start, + DISPLAY_LINE_YPOS (dl), clip_end - clip_start, height); for (i = 0; i < nruns; i++) @@ -881,7 +895,7 @@ the given font. It is possible that a font is being displayed on a line taller than it is, so this would cause us to fail to clear some areas. */ - if ((int) fi->height < (int) (height + dl->clip)) + if ((int) fi->height < (int) (height + dl->clip + dl->top_clip)) { int clear_start = max (xpos, clip_start); int clear_end = min (xpos + this_width, clip_end); @@ -892,8 +906,8 @@ ypos1_string = dl->ypos - fi->ascent; ypos2_string = dl->ypos + fi->descent; - ypos1_line = dl->ypos - dl->ascent; - ypos2_line = dl->ypos + dl->descent - dl->clip; + ypos1_line = DISPLAY_LINE_YPOS (dl); + ypos2_line = ypos1_line + DISPLAY_LINE_HEIGHT (dl); /* Make sure we don't clear below the real bottom of the line. */ @@ -919,7 +933,7 @@ else { redisplay_clear_region (window, findex, clear_start, - dl->ypos - dl->ascent, clear_end - clear_start, + DISPLAY_LINE_YPOS (dl), clear_end - clear_start, height); } } @@ -952,7 +966,7 @@ clip_box[0].width = clip_end - clip_start; clip_box[0].height = height; - XSetClipRectangles (dpy, gc, clip_start, dl->ypos - dl->ascent, + XSetClipRectangles (dpy, gc, clip_start, DISPLAY_LINE_YPOS (dl), clip_box, 1, Unsorted); } @@ -1052,7 +1066,7 @@ clip_box[0].width = cursor_width; clip_box[0].height = height; - XSetClipRectangles (dpy, cgc, cursor_start, dl->ypos - dl->ascent, + XSetClipRectangles (dpy, cgc, cursor_start, DISPLAY_LINE_YPOS (dl), clip_box, 1, Unsorted); if (runs[i].dimension == 1) @@ -1112,12 +1126,12 @@ tmp_y = dl->ypos - bogusly_obtained_ascent_value; tmp_height = cursor_height; - if (tmp_y + tmp_height > (int) (dl->ypos - dl->ascent + height)) + if (tmp_y + tmp_height > (int) (DISPLAY_LINE_YPOS(dl) + height)) { - tmp_y = dl->ypos - dl->ascent + height - tmp_height; - if (tmp_y < (int) (dl->ypos - dl->ascent)) - tmp_y = dl->ypos - dl->ascent; - tmp_height = dl->ypos - dl->ascent + height - tmp_y; + tmp_y = DISPLAY_LINE_YPOS (dl) + height - tmp_height; + if (tmp_y < (int) DISPLAY_LINE_YPOS (dl)) + tmp_y = DISPLAY_LINE_YPOS (dl); + tmp_height = DISPLAY_LINE_YPOS (dl) + height - tmp_y; } if (need_clipping) @@ -1153,9 +1167,9 @@ void x_output_x_pixmap (struct frame *f, struct Lisp_Image_Instance *p, int x, - int y, int clip_x, int clip_y, int clip_width, - int clip_height, int width, int height, int pixmap_offset, - unsigned long fg, unsigned long bg, GC override_gc) + int y, int xoffset, int yoffset, + int width, int height, unsigned long fg, unsigned long bg, + GC override_gc) { struct device *d = XDEVICE (f->device); Display *dpy = DEVICE_X_DISPLAY (d); @@ -1164,7 +1178,6 @@ GC gc; XGCValues gcv; unsigned long pixmap_mask; - int need_clipping = (clip_x || clip_y); if (!override_gc) { @@ -1178,17 +1191,16 @@ { gcv.function = GXcopy; gcv.clip_mask = IMAGE_INSTANCE_X_MASK (p); - gcv.clip_x_origin = x; - gcv.clip_y_origin = y - pixmap_offset; + gcv.clip_x_origin = x - xoffset; + gcv.clip_y_origin = y - yoffset; pixmap_mask |= (GCFunction | GCClipMask | GCClipXOrigin | GCClipYOrigin); - /* Can't set a clip rectangle below because we already have a mask. - We could conceivably create a new clipmask by zeroing out - everything outside the clip region. Is it worth it? + /* Can't set a clip rectangle because we already have a mask. Is it possible to get an equivalent effect by changing the args to XCopyArea below rather than messing with a clip box? - - dkindred@cs.cmu.edu */ - need_clipping = 0; + - dkindred@cs.cmu.edu + Yes. We don't clip at all now - andy@xemacs.org + */ } gc = gc_cache_lookup (DEVICE_X_GC_CACHE (d), &gcv, pixmap_mask); @@ -1199,19 +1211,6 @@ /* override_gc might have a mask already--we don't want to nuke it. Maybe we can insist that override_gc have no mask, or use one of the suggestions above. */ - need_clipping = 0; - } - - if (need_clipping) - { - XRectangle clip_box[1]; - - clip_box[0].x = clip_x; - clip_box[0].y = clip_y; - clip_box[0].width = clip_width; - clip_box[0].height = clip_height; - - XSetClipRectangles (dpy, gc, x, y, clip_box, 1, Unsorted); } /* depth of 0 means it's a bitmap, not a pixmap, and we should use @@ -1220,126 +1219,33 @@ pixel values, instead of symbolic of fg/bg. */ if (IMAGE_INSTANCE_PIXMAP_DEPTH (p) > 0) { - XCopyArea (dpy, IMAGE_INSTANCE_X_PIXMAP (p), x_win, gc, 0, - pixmap_offset, width, + XCopyArea (dpy, + IMAGE_INSTANCE_X_PIXMAP_SLICE + (p, IMAGE_INSTANCE_PIXMAP_SLICE (p)), x_win, gc, xoffset, + yoffset, width, height, x, y); } else { - XCopyPlane (dpy, IMAGE_INSTANCE_X_PIXMAP (p), x_win, gc, 0, - (pixmap_offset < 0 - ? 0 - : pixmap_offset), - width, height, x, - (pixmap_offset < 0 - ? y - pixmap_offset - : y), - 1L); - } - - if (need_clipping) - { - XSetClipMask (dpy, gc, None); - XSetClipOrigin (dpy, gc, 0, 0); + XCopyPlane (dpy, IMAGE_INSTANCE_X_PIXMAP_SLICE + (p, IMAGE_INSTANCE_PIXMAP_SLICE (p)), x_win, gc, + xoffset, yoffset, width, height, x, y, 1L); } } static void -x_output_pixmap (struct window *w, struct display_line *dl, - Lisp_Object image_instance, int xpos, int xoffset, - int start_pixpos, int width, face_index findex, - int cursor_start, int cursor_width, int cursor_height) +x_output_pixmap (struct window *w, Lisp_Object image_instance, + struct display_box *db, struct display_glyph_area *dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height, int bg_pixmap) { struct frame *f = XFRAME (w->frame); struct device *d = XDEVICE (f->device); struct Lisp_Image_Instance *p = XIMAGE_INSTANCE (image_instance); - Lisp_Object window; Display *dpy = DEVICE_X_DISPLAY (d); Window x_win = XtWindow (FRAME_X_TEXT_WIDGET (f)); - int lheight = dl->ascent + dl->descent - dl->clip; - int pheight = ((int) IMAGE_INSTANCE_PIXMAP_HEIGHT (p) > lheight ? lheight : - IMAGE_INSTANCE_PIXMAP_HEIGHT (p)); - int pwidth = min (width + xoffset, (int) IMAGE_INSTANCE_PIXMAP_WIDTH (p)); - int clip_x, clip_y, clip_width, clip_height; - - /* The pixmap_offset is used to center the pixmap on lines which are - shorter than it is. This results in odd effects when scrolling - pixmaps off of the bottom. Let's try not using it. */ -#if 0 - int pixmap_offset = (int) (IMAGE_INSTANCE_PIXMAP_HEIGHT (p) - lheight) / 2; -#else - int pixmap_offset = 0; -#endif - - XSETWINDOW (window, w); - - if ((start_pixpos >= 0 && start_pixpos > xpos) || xoffset) - { - if (start_pixpos > xpos && start_pixpos > xpos + width) - return; - - clip_x = xoffset; - clip_width = width; - if (start_pixpos > xpos) - { - clip_x += (start_pixpos - xpos); - clip_width -= (start_pixpos - xpos); - } - } - else - { - clip_x = 0; - clip_width = 0; - } - - /* Place markers for possible future functionality (clipping the top - half instead of the bottom half; think pixel scrolling). */ - clip_y = 0; - clip_height = pheight; - - /* Clear the area the pixmap is going into. The pixmap itself will - always take care of the full width. We don't want to clear where - it is going to go in order to avoid flicker. So, all we have to - take care of is any area above or below the pixmap. */ - /* #### We take a shortcut for now. We know that since we have - pixmap_offset hardwired to 0 that the pixmap is against the top - edge so all we have to worry about is below it. */ - /* #### Unless the pixmap has a mask in which case we have to clear - the whole damn thing since we can't yet clear just the area not - included in the mask. */ - if (((int) (dl->ypos - dl->ascent + pheight) < - (int) (dl->ypos + dl->descent - dl->clip)) - || IMAGE_INSTANCE_X_MASK (p)) - { - int clear_x, clear_y, clear_width, clear_height; - - if (IMAGE_INSTANCE_X_MASK (p)) - { - clear_y = dl->ypos - dl->ascent; - clear_height = lheight; - } - else - { - clear_y = dl->ypos - dl->ascent + pheight; - clear_height = lheight - pheight; - } - - if (start_pixpos >= 0 && start_pixpos > xpos) - { - clear_x = start_pixpos; - clear_width = xpos + width - start_pixpos; - } - else - { - clear_x = xpos; - clear_width = width; - } - - redisplay_clear_region (window, findex, clear_x, clear_y, - clear_width, clear_height); - } - + /* Output the pixmap. */ { Lisp_Object tmp_pixel; @@ -1350,20 +1256,19 @@ tmp_pixel = WINDOW_FACE_CACHEL_BACKGROUND (w, findex); tmp_bcolor = COLOR_INSTANCE_X_COLOR (XCOLOR_INSTANCE (tmp_pixel)); - x_output_x_pixmap (f, p, xpos - xoffset, dl->ypos - dl->ascent, clip_x, - clip_y, clip_width, clip_height, - pwidth, pheight, pixmap_offset, + x_output_x_pixmap (f, p, db->xpos, db->ypos, + dga->xoffset, dga->yoffset, + dga->width, dga->height, tmp_fcolor.pixel, tmp_bcolor.pixel, 0); } /* Draw a cursor over top of the pixmap. */ - if (cursor_width && cursor_height && (cursor_start >= xpos) + if (cursor_width && cursor_height && (cursor_start >= db->xpos) && !NILP (w->text_cursor_visible_p) - && (cursor_start < xpos + pwidth)) + && (cursor_start < db->xpos + dga->width)) { GC gc; int focus = EQ (w->frame, DEVICE_FRAME_WITH_FOCUS_REAL (d)); - int y = dl->ypos - dl->ascent; struct face_cachel *cursor_cachel = WINDOW_FACE_CACHEL (w, get_builtin_face_cache_index @@ -1371,17 +1276,17 @@ gc = x_get_gc (d, Qnil, cursor_cachel->background, Qnil, Qnil, Qnil); - if (cursor_width > xpos + pwidth - cursor_start) - cursor_width = xpos + pwidth - cursor_start; + if (cursor_width > db->xpos + dga->width - cursor_start) + cursor_width = db->xpos + dga->width - cursor_start; if (focus) { - XFillRectangle (dpy, x_win, gc, cursor_start, y, cursor_width, + XFillRectangle (dpy, x_win, gc, cursor_start, db->ypos, cursor_width, cursor_height); } else { - XDrawRectangle (dpy, x_win, gc, cursor_start, y, cursor_width, + XDrawRectangle (dpy, x_win, gc, cursor_start, db->ypos, cursor_width, cursor_height); } } @@ -1404,6 +1309,7 @@ XColor tmp_color; XGCValues gcv; GC background_gc; + enum edge_style style; unsigned long mask; int x, y1, y2, width, shadow_thickness, spacing, line_width; @@ -1439,10 +1345,20 @@ x + spacing + shadow_thickness, y1, line_width, y2 - y1); + if (shadow_thickness < 0) + { + shadow_thickness = -shadow_thickness; + style = EDGE_BEVEL_IN; + } + else + { + style = EDGE_BEVEL_OUT; + } + /* Draw the shadows around the divider line */ x_bevel_area (w, div_face, x + spacing, y1, width - 2 * spacing, y2 - y1, - shadow_thickness); + shadow_thickness, EDGE_ALL, style); } /***************************************************************************** @@ -1471,9 +1387,12 @@ buffer); int x = rb->xpos; - int y = dl->ypos - dl->ascent; + int y = DISPLAY_LINE_YPOS (dl); int width = rb->width; - int height = dl->ascent + dl->descent - dl->clip; + int height = DISPLAY_LINE_HEIGHT (dl); + + /* Unmap all subwindows in the area we are going to blank. */ + redisplay_unmap_subwindows_maybe (f, x, y, width, height); if (start_pixpos > x) { @@ -1567,10 +1486,10 @@ int x = rb->xpos; int width = rb->width; - int height = dl->ascent + dl->descent - dl->clip; + int height = DISPLAY_LINE_HEIGHT (dl); int ypos1, ypos2, ypos3, ypos4; - ypos1 = dl->ypos - dl->ascent; + ypos1 = DISPLAY_LINE_YPOS (dl); ypos2 = ypos1 + rb->object.hline.yoffset; ypos3 = ypos2 + rb->object.hline.thickness; ypos4 = dl->ypos + dl->descent - dl->clip; @@ -1609,7 +1528,7 @@ void x_output_shadows (struct frame *f, int x, int y, int width, int height, GC top_shadow_gc, GC bottom_shadow_gc, GC background_gc, - int shadow_thickness) + int shadow_thickness, int edges) { struct device *d = XDEVICE (f->device); @@ -1631,28 +1550,41 @@ for (elt = 0; elt < shadow_thickness; elt++) { int seg1 = elt; - int seg2 = elt + shadow_thickness; - - top_shadow[seg1].x1 = x; - top_shadow[seg1].x2 = x + width - elt - 1; - top_shadow[seg1].y1 = top_shadow[seg1].y2 = y + elt; + int seg2 = (edges & EDGE_TOP) ? elt + shadow_thickness : elt; + int bot_seg2 = (edges & EDGE_BOTTOM) ? elt + shadow_thickness : elt; - top_shadow[seg2].x1 = top_shadow[seg2].x2 = x + elt; - top_shadow[seg2].y1 = y + shadow_thickness; - top_shadow[seg2].y2 = y + height - elt - 1; - - bottom_shadow[seg1].x1 = x + elt + 1; - bottom_shadow[seg1].x2 = x + width - 1; - bottom_shadow[seg1].y1 = bottom_shadow[seg1].y2 = y + height - elt - 1; - - bottom_shadow[seg2].x1 = bottom_shadow[seg2].x2 = x + width - elt - 1; - bottom_shadow[seg2].y1 = y + elt + 1; - bottom_shadow[seg2].y2 = y + height - shadow_thickness; + if (edges & EDGE_TOP) + { + top_shadow[seg1].x1 = x + elt; + top_shadow[seg1].x2 = x + width - elt - 1; + top_shadow[seg1].y1 = top_shadow[seg1].y2 = y + elt; + } + if (edges & EDGE_LEFT) + { + top_shadow[seg2].x1 = top_shadow[seg2].x2 = x + elt; + top_shadow[seg2].y1 = y + elt; + top_shadow[seg2].y2 = y + height - elt - 1; + } + if (edges & EDGE_BOTTOM) + { + bottom_shadow[seg1].x1 = x + elt; + bottom_shadow[seg1].x2 = x + width - elt - 1; + bottom_shadow[seg1].y1 = bottom_shadow[seg1].y2 = y + height - elt - 1; + } + if (edges & EDGE_RIGHT) + { + bottom_shadow[bot_seg2].x1 = bottom_shadow[bot_seg2].x2 = x + width - elt - 1; + bottom_shadow[bot_seg2].y1 = y + elt; + bottom_shadow[bot_seg2].y2 = y + height - elt - 1; + } } - XDrawSegments (dpy, x_win, top_shadow_gc, top_shadow, shadow_thickness * 2); + XDrawSegments (dpy, x_win, top_shadow_gc, top_shadow, + ((edges & EDGE_TOP) ? shadow_thickness : 0) + + ((edges & EDGE_LEFT) ? shadow_thickness : 0)); XDrawSegments (dpy, x_win, bottom_shadow_gc, bottom_shadow, - shadow_thickness * 2); + ((edges & EDGE_BOTTOM) ? shadow_thickness : 0) + + ((edges & EDGE_RIGHT) ? shadow_thickness : 0)); } /***************************************************************************** @@ -1923,9 +1855,9 @@ WINDOW_BUFFER (w)); int x = xpos; - int y = dl->ypos - dl->ascent; + int y = DISPLAY_LINE_YPOS (dl); int width = EOL_CURSOR_WIDTH; - int height = dl->ascent + dl->descent - dl->clip; + int height = DISPLAY_LINE_HEIGHT (dl); int cursor_height, cursor_y; int defheight, defascent; @@ -2153,4 +2085,6 @@ CONSOLE_HAS_METHOD (x, flash); CONSOLE_HAS_METHOD (x, ring_bell); CONSOLE_HAS_METHOD (x, bevel_area); + CONSOLE_HAS_METHOD (x, output_string); + CONSOLE_HAS_METHOD (x, output_pixmap); } diff -r 28d9c139be4c -r 11054d720c21 src/redisplay.c --- a/src/redisplay.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/redisplay.c Mon Aug 13 11:26:11 2007 +0200 @@ -154,6 +154,10 @@ (those off the left side of the screen) need to be skipped before anything is displayed. */ Bytind bi_start_col_enabled; + int start_col_xoffset; /* Number of pixels that still need to + be skipped. This is used for + horizontal scrolling of glyphs, where we want + to be able to scroll over part of the glyph. */ int hscroll_glyph_width_adjust; /* how much the width of the hscroll glyph differs from space_width (w). @@ -259,8 +263,7 @@ int pos_type, int allow_cursor, struct glyph_cachel *cachel); static Bytind create_text_block (struct window *w, struct display_line *dl, - Bytind bi_start_pos, int start_col, - prop_block_dynarr **prop, + Bytind bi_start_pos, prop_block_dynarr **prop, int type); static int create_overlay_glyph_block (struct window *w, struct display_line *dl); @@ -275,9 +278,6 @@ static void update_line_start_cache (struct window *w, Bufpos from, Bufpos to, Bufpos point, int no_regen); static int point_visible (struct window *w, Bufpos point, int type); -extern Bytind bi_find_next_emchar_in_string (struct Lisp_String* str, Emchar target, - Bytind st, EMACS_INT count); -extern int string_column_at_point (struct Lisp_String* s, Bufpos init_pos, int tab_width); /* This used to be 10 but 30 seems to give much better performance. */ #define INIT_MAX_PREEMPTS 30 @@ -302,8 +302,8 @@ /* Used by generate_formatted_string. Global because they get used so much that the dynamic allocation time adds up. */ -Emchar_dynarr *formatted_string_emchar_dynarr; -struct display_line formatted_string_display_line; +static Emchar_dynarr *formatted_string_emchar_dynarr; +static struct display_line formatted_string_display_line; /* We store the extents that we need to generate in a Dynarr and then frob them all on at the end of generating the string. We do it this way rather than adding them as we generate the string because @@ -311,9 +311,9 @@ (to avoid having to resize the string multiple times), and we don't want to go around adding extents to a string when the extents might stretch off the end of the string. */ -EXTENT_dynarr *formatted_string_extent_dynarr; -Bytecount_dynarr *formatted_string_extent_start_dynarr; -Bytecount_dynarr *formatted_string_extent_end_dynarr; +static EXTENT_dynarr *formatted_string_extent_dynarr; +static Bytecount_dynarr *formatted_string_extent_start_dynarr; +static Bytecount_dynarr *formatted_string_extent_end_dynarr; /* #### probably temporary */ @@ -338,7 +338,7 @@ int horizontal_clip; /* Set if currently inside update_line_start_cache. */ -int updating_line_start_cache; +static int updating_line_start_cache; /* Nonzero means reading single-character input with prompt so put cursor on minibuffer after the prompt. */ @@ -378,6 +378,11 @@ int subwindows_changed; int subwindows_changed_set; +/* non-zero if any displayed subwindow is in need of updating + somewhere. */ +int subwindows_state_changed; +int subwindows_state_changed_set; + /* This variable is 1 if the icon has to be updated. It is set to 1 when `frame-icon-glyph' changes. */ int icon_changed; @@ -453,7 +458,7 @@ Lisp_Object Voverlay_arrow_string; Lisp_Object Vwindow_size_change_functions; -Lisp_Object Qwindow_scroll_functions, Vwindow_scroll_functions; +Lisp_Object Vwindow_scroll_functions; Lisp_Object Qredisplay_end_trigger_functions, Vredisplay_end_trigger_functions; #define INHIBIT_REDISPLAY_HOOKS /* #### Until we've thought about @@ -465,7 +470,7 @@ Lisp_Object Qpre_redisplay_hook, Qpost_redisplay_hook; #endif /* INHIBIT_REDISPLAY_HOOKS */ -int last_display_warning_tick, display_warning_tick; +static int last_display_warning_tick, display_warning_tick; Lisp_Object Qdisplay_warning_buffer; int inhibit_warning_display; @@ -475,6 +480,10 @@ Lisp_Object Vtext_cursor_visible_p; int column_number_start_at_one; + +#define WINDOW_SCROLLED(w) \ +(w->hscroll > 0 || w->left_xoffset) + /***************************************************************************/ /* */ @@ -644,8 +653,8 @@ int pix_tab_width = tab_pix_width (w); /* Adjust n_pos for any hscrolling which has happened. */ - if (w->hscroll > 1) - n_pos -= space_width (w) * (w->hscroll - 1); + if (WINDOW_SCROLLED (w)) + n_pos -= space_width (w) * (w->hscroll - 1) + w->left_xoffset; while (n_pos <= start_pixpos) n_pos += pix_tab_width; @@ -697,8 +706,7 @@ static Bufpos generate_display_line (struct window *w, struct display_line *dl, int bounds, - Bufpos start_pos, int start_col, - prop_block_dynarr **prop, + Bufpos start_pos, prop_block_dynarr **prop, int type) { Bufpos ret_bufpos; @@ -731,7 +739,7 @@ /* #### urk urk urk!!! Chuck fix this shit! */ Bytind hacked_up_bytind = create_text_block (w, dl, bufpos_to_bytind (b, start_pos), - start_col, prop, type); + prop, type); if (hacked_up_bytind > BI_BUF_ZV (b)) ret_bufpos = BUF_ZV (b) + 1; else @@ -1548,7 +1556,7 @@ if (!width) return NULL; - if (data->start_col) + if (data->start_col || data->start_col_xoffset) { prop_block_dynarr *retval; int glyph_char_width = width / space_width (w); @@ -1782,8 +1790,7 @@ static Bytind create_text_block (struct window *w, struct display_line *dl, - Bytind bi_start_pos, int start_col, - prop_block_dynarr **prop, + Bytind bi_start_pos, prop_block_dynarr **prop, int type) { struct frame *f = XFRAME (w->frame); @@ -1927,6 +1934,7 @@ data.cursor_x = -1; data.start_col = w->hscroll; + data.start_col_xoffset = w->left_xoffset; data.bi_start_col_enabled = (w->hscroll ? bi_start_pos : 0); data.hscroll_glyph_width_adjust = 0; @@ -2246,6 +2254,7 @@ data.blank_width = DEVMETH (d, eol_cursor_width, ()); data.findex = DEFAULT_INDEX; data.start_col = 0; + data.start_col_xoffset = 0; data.bi_start_col_enabled = 0; add_emchar_rune (&data); @@ -2279,7 +2288,8 @@ int prop_width = 0; if (data.start_col > 1) - tab_start_pixpos -= (space_width (w) * (data.start_col - 1)); + tab_start_pixpos -= (space_width (w) * (data.start_col - 1)) + + data.start_col_xoffset; next_tab_start = next_tab_position (w, tab_start_pixpos, @@ -2486,6 +2496,7 @@ data.blank_width = DEVMETH (d, eol_cursor_width, ()); data.findex = DEFAULT_INDEX; data.start_col = 0; + data.start_col_xoffset = 0; data.bi_start_col_enabled = 0; data.max_pixpos += data.blank_width; @@ -4234,8 +4245,10 @@ struct frame *f = XFRAME (w->frame); /* Note that a lot of the buffer controlled stuff has been left in because you might well want to make use of it (selective display - etc), its just the buffer text that we do not use. */ - struct buffer *b = XBUFFER (w->buffer); + etc), its just the buffer text that we do not use. However, it + seems to be possible for buffer to be nil sometimes so protect + against this case. */ + struct buffer *b = BUFFERP (w->buffer) ? XBUFFER (w->buffer) : 0; struct device *d = XDEVICE (f->device); struct Lisp_String* s = XSTRING (disp_string); @@ -4246,7 +4259,7 @@ pos_data data; - int truncate_win = window_truncation_on (w); + int truncate_win = b ? window_truncation_on (w) : 0; int end_glyph_width = 0; /* we're going to ditch selective display for static text, its an @@ -4296,10 +4309,10 @@ Since more than one display table is possible, you have great flexibility in mapping ranges of characters. */ - Emchar printable_min = (CHAR_OR_CHAR_INTP (b->ctl_arrow) + Emchar printable_min = b ? (CHAR_OR_CHAR_INTP (b->ctl_arrow) ? XCHAR_OR_CHAR_INT (b->ctl_arrow) : ((EQ (b->ctl_arrow, Qt) || EQ (b->ctl_arrow, Qnil)) - ? 255 : 160)); + ? 255 : 160)) : 255; Lisp_Object face_dt, window_dt; @@ -4730,27 +4743,10 @@ } else if (data.bi_bufpos == bi_string_zv) { - /* We need to add a marker to the end of the line since there is no - newline character in order for the cursor to get drawn. We label - it as a newline so that it gets handled correctly by the - whitespace routines below. */ - - data.ch = '\n'; - data.blank_width = DEVMETH (d, eol_cursor_width, ()); - data.findex = default_face; - data.start_col = 0; - data.bi_start_col_enabled = 0; - - data.max_pixpos += data.blank_width; - add_emchar_rune (&data); - data.max_pixpos -= data.blank_width; - - /* #### urk! Chuck, this shit is bad news. Going around - manipulating invalid positions is guaranteed to result in - trouble sooner or later. */ - data.bi_bufpos = bi_string_zv + 1; - } - + /* create_text_block () adds a bogus \n marker here which screws + up subwindow display. Since we never have a cursor in the + gutter we can safely ignore it. */ + } /* Calculate left whitespace boundary. */ { int elt = 0; @@ -4854,7 +4850,7 @@ dl->end_bufpos = buffer_or_string_bytind_to_bufpos (disp_string, data.bi_bufpos) - 1; if (truncate_win) data.dl->num_chars = - string_column_at_point (s, dl->end_bufpos, XINT (b->tab_width)); + string_column_at_point (s, dl->end_bufpos, b ? XINT (b->tab_width) : 8); else /* This doesn't correctly take into account tabs and control characters but if the window isn't being truncated then this @@ -4909,7 +4905,7 @@ Bufpos ret_bufpos; /* you must set bounds before calling this. */ - + /* Reset what this line is using. */ if (dl->display_blocks) Dynarr_reset (dl->display_blocks); @@ -4970,7 +4966,7 @@ if (NILP (disp_string)) return; - s_zv = XSTRING_CHAR_LENGTH (disp_string) - 1; + s_zv = XSTRING_CHAR_LENGTH (disp_string); bounds.left_out = xpos; bounds.right_out = xpos + width; @@ -5066,6 +5062,7 @@ struct buffer *b = XBUFFER (w->buffer); int ypos = WINDOW_TEXT_TOP (w); int yend; /* set farther down */ + int yclip = WINDOW_TEXT_TOP_CLIP (w); prop_block_dynarr *prop; layout_bounds bounds; @@ -5140,17 +5137,37 @@ dlp->bounds = bounds; dlp->offset = 0; - start_pos = generate_display_line (w, dlp, 1, start_pos, - w->hscroll, &prop, type); - dlp->ypos = ypos + dlp->ascent; + start_pos = generate_display_line (w, dlp, 1, start_pos, &prop, type); + + if (yclip > dlp->ascent) + { + /* this should never happen, but if it does just display the + whole line */ + yclip = 0; + } + + dlp->ypos = (ypos + dlp->ascent) - yclip; ypos = dlp->ypos + dlp->descent; + /* See if we've been asked to start midway through a line, for + partial display line scrolling. */ + if (yclip) + { + dlp->top_clip = yclip; + yclip = 0; + } + else + dlp->top_clip = 0; + if (ypos > yend) { int visible_height = dlp->ascent + dlp->descent; dlp->clip = (ypos - yend); - visible_height -= dlp->clip; + /* Although this seems strange we could have a single very + tall line visible for which we need to account for both + the top clip and the bottom clip. */ + visible_height -= (dlp->clip + dlp->top_clip); if (visible_height < VERTICAL_CLIP (w, 1)) { @@ -5393,7 +5410,7 @@ return 0; new_start = generate_display_line (w, ddl, 0, ddl->bufpos + ddl->offset, - w->hscroll, &prop, DESIRED_DISP); + &prop, DESIRED_DISP); ddl->offset = 0; /* #### If there is propagated stuff the fail. We could @@ -5412,6 +5429,7 @@ if (cdl->ypos != ddl->ypos || cdl->ascent != ddl->ascent || cdl->descent != ddl->descent + || cdl->top_clip != ddl->top_clip || (cdl->cursor_elt != -1 && ddl->cursor_elt == -1) || (cdl->cursor_elt == -1 && ddl->cursor_elt != -1) || old_start != ddl->bufpos @@ -5555,7 +5573,7 @@ return 0; new_start = generate_display_line (w, ddl, 0, ddl->bufpos + ddl->offset, - w->hscroll, &prop, DESIRED_DISP); + &prop, DESIRED_DISP); ddl->offset = 0; /* If there is propagated stuff then it is pretty much a @@ -5585,6 +5603,7 @@ if (cdl->ypos != ddl->ypos || cdl->ascent != ddl->ascent || cdl->descent != ddl->descent + || cdl->top_clip != ddl->top_clip || (cdl->cursor_elt != -1 && ddl->cursor_elt == -1) || (cdl->cursor_elt == -1 && ddl->cursor_elt != -1)) { @@ -5877,10 +5896,11 @@ else mark_face_cachels_as_not_updated (w); - /* Ditto the glyph cache elements. */ + /* Ditto the glyph cache elements, although we do *not* invalidate + the cache purely because glyphs have changed - this is now + handled by the dirty flag.*/ if ((!echo_active && b != window_display_buffer (w)) - || !Dynarr_length (w->glyph_cachels) - || f->glyphs_changed) + || !Dynarr_length (w->glyph_cachels)) reset_glyph_cachels (w); else mark_glyph_cachels_as_not_updated (w); @@ -5966,6 +5986,7 @@ && !f->faces_changed && !f->glyphs_changed && !f->subwindows_changed + && !f->subwindows_state_changed && !f->point_changed && !f->windows_structure_changed) { @@ -5987,6 +6008,7 @@ && !f->faces_changed && !f->glyphs_changed && !f->subwindows_changed + && !f->subwindows_state_changed && !f->windows_structure_changed) { if (point_visible (w, pointm, CURRENT_DISP) @@ -6045,6 +6067,7 @@ && !f->faces_changed && !f->glyphs_changed && !f->subwindows_changed + && !f->subwindows_state_changed && !f->windows_structure_changed && !f->frame_changed && !truncation_changed @@ -6141,6 +6164,10 @@ somewhere else once tty updates occur on a per-frame basis. */ mark_face_cachels_as_clean (w); + /* The glyph cachels only get dirty if someone changed something. */ + if (glyphs_changed) + mark_glyph_cachels_as_clean (w); + w->windows_changed = 0; } @@ -6262,7 +6289,6 @@ being handled. */ update_frame_menubars (f); #endif /* HAVE_MENUBARS */ - update_frame_gutters (f); /* widgets are similar to menus in that they can call lisp to determine activation etc. Therefore update them before we get into redisplay. This is primarily for connected widgets such as @@ -6273,6 +6299,30 @@ update_frame_toolbars (f); #endif /* HAVE_TOOLBARS */ + /* If we clear the frame we have to force its contents to be redrawn. */ + if (f->clear) + f->frame_changed = 1; + + /* invalidate the subwindow cache. We use subwindows_changed here to + cause subwindows to get instantiated. This is because + subwindows_state_changed is less strict - dealing with things + like the clicked state of button. We have to do this before + redisplaying the gutters as subwindows get unmapped in the + process.*/ + if (!Dynarr_length (f->subwindow_cachels) + || f->subwindows_changed + || f->frame_changed) + { + reset_subwindow_cachels (f); + /* we have to do this so the gutter gets regenerated. */ + reset_gutter_display_lines (f); + } + else + mark_subwindow_cachels_as_not_updated (f); + /* We can now update the gutters, safe in the knowledge that our + efforts won't get undone. */ + update_frame_gutters (f); + hold_frame_size_changes (); /* ----------------- BEGIN CRITICAL REDISPLAY SECTION ---------------- */ @@ -6299,27 +6349,12 @@ #### If a frame-size change does occur we should probably actually be preempting redisplay. */ - /* If we clear the frame we have to force its contents to be redrawn. */ - if (f->clear) - f->frame_changed = 1; - /* Erase the frame before outputting its contents. */ if (f->clear) { DEVMETH (d, clear_frame, (f)); } - /* invalidate the subwindow cache. we are going to reuse the glyphs - flag here to cause subwindows to get instantiated. This is - because subwindows changed is less strict - dealing with things - like the clicked state of button. */ - if (!Dynarr_length (f->subwindow_cachels) - || f->glyphs_changed - || f->frame_changed) - reset_subwindow_cachels (f); - else - mark_subwindow_cachels_as_not_updated (f); - /* Do the selected window first. */ redisplay_window (FRAME_SELECTED_WINDOW (f), 0); @@ -6334,24 +6369,9 @@ update_frame_title (f); - f->buffers_changed = 0; - f->clip_changed = 0; - f->extents_changed = 0; - f->faces_changed = 0; - f->frame_changed = 0; - f->glyphs_changed = 0; - f->subwindows_changed = 0; - f->icon_changed = 0; - f->menubar_changed = 0; - f->modeline_changed = 0; - f->point_changed = 0; - f->toolbar_changed = 0; - f->gutter_changed = 0; - f->windows_changed = 0; - f->windows_structure_changed = 0; + CLASS_RESET_CHANGED_FLAGS (f); f->window_face_cache_reset = 0; f->echo_area_garbaged = 0; - f->clear = 0; if (!f->size_change_pending) @@ -6401,12 +6421,7 @@ if (FRAME_REPAINT_P (f)) { - if (f->buffers_changed || f->clip_changed || f->extents_changed || - f->faces_changed || f->frame_changed || f->menubar_changed || - f->modeline_changed || f->point_changed || f->size_changed || - f->toolbar_changed || f->windows_changed || f->size_slipped || - f->windows_structure_changed || f->glyphs_changed || - f->subwindows_changed || f->gutter_changed) + if (CLASS_REDISPLAY_FLAGS_CHANGEDP(f)) { preempted = redisplay_frame (f, 0); } @@ -6436,12 +6451,8 @@ if (FRAME_REPAINT_P (f)) { - if (f->buffers_changed || f->clip_changed || f->extents_changed || - f->faces_changed || f->frame_changed || f->menubar_changed || - f->modeline_changed || f->point_changed || f->size_changed || - f->toolbar_changed || f->windows_changed || - f->windows_structure_changed || f->gutter_changed || - f->glyphs_changed || f->subwindows_changed) + if (CLASS_REDISPLAY_FLAGS_CHANGEDP(f) + || f->size_changed) { preempted = redisplay_frame (f, 0); } @@ -6456,21 +6467,7 @@ /* If we get here then we redisplayed all of our frames without getting preempted so mark ourselves as clean. */ - d->buffers_changed = 0; - d->clip_changed = 0; - d->extents_changed = 0; - d->faces_changed = 0; - d->frame_changed = 0; - d->glyphs_changed = 0; - d->subwindows_changed = 0; - d->icon_changed = 0; - d->menubar_changed = 0; - d->modeline_changed = 0; - d->point_changed = 0; - d->toolbar_changed = 0; - d->gutter_changed = 0; - d->windows_changed = 0; - d->windows_structure_changed = 0; + CLASS_RESET_CHANGED_FLAGS (d); if (!size_change_failed) d->size_changed = 0; @@ -6505,13 +6502,8 @@ if (asynch_device_change_pending) handle_asynch_device_change (); - if (!buffers_changed && !clip_changed && !extents_changed && - !faces_changed && !frame_changed && !icon_changed && - !menubar_changed && !modeline_changed && !point_changed && - !size_changed && !toolbar_changed && !windows_changed && - !glyphs_changed && !subwindows_changed && - !gutter_changed && !windows_structure_changed && - !disable_preemption && preemption_count < max_preempts) + if (!GLOBAL_REDISPLAY_FLAGS_CHANGEDP && + !size_changed && !disable_preemption && preemption_count < max_preempts) goto done; DEVICE_LOOP_NO_BREAK (devcons, concons) @@ -6519,12 +6511,8 @@ struct device *d = XDEVICE (XCAR (devcons)); int preempted; - if (d->buffers_changed || d->clip_changed || d->extents_changed || - d->faces_changed || d->frame_changed || d->icon_changed || - d->menubar_changed || d->modeline_changed || d->point_changed || - d->size_changed || d->toolbar_changed || d->windows_changed || - d->windows_structure_changed || d->gutter_changed || - d->glyphs_changed || d->subwindows_changed) + if (CLASS_REDISPLAY_FLAGS_CHANGEDP (d) + || d->size_changed) { preempted = redisplay_device (d); @@ -6543,20 +6531,7 @@ preemption_count = 0; /* Mark redisplay as accurate */ - buffers_changed = 0; - clip_changed = 0; - extents_changed = 0; - frame_changed = 0; - glyphs_changed = 0; - subwindows_changed = 0; - icon_changed = 0; - menubar_changed = 0; - modeline_changed = 0; - point_changed = 0; - toolbar_changed = 0; - gutter_changed = 0; - windows_changed = 0; - windows_structure_changed = 0; + GLOBAL_RESET_CHANGED_FLAGS; RESET_CHANGED_SET_FLAGS; if (faces_changed) @@ -6787,7 +6762,6 @@ case 'p': { Bufpos pos = marker_position (w->start[type]); - Charcount total = BUF_ZV (b) - BUF_BEGV (b); /* This had better be while the desired lines are being done. */ if (w->window_end_pos[type] <= BUF_Z (b) - BUF_ZV (b)) @@ -6804,15 +6778,20 @@ /* This hard limit is ok since the string it will hold has a fixed maximum length of 3. But just to be safe... */ char buf[10]; - - total = ((pos - BUF_BEGV (b)) * 100 + total - 1) / total; + Charcount chars = pos - BUF_BEGV (b); + Charcount total = BUF_ZV (b) - BUF_BEGV (b); + + /* Avoid overflow on big buffers */ + int percent = total > LONG_MAX/200 ? + (chars + total/200) / (total / 100) : + (chars * 100 + total/2) / total; /* We can't normally display a 3-digit number, so get us a 2-digit number that is close. */ - if (total == 100) - total = 99; - - sprintf (buf, "%2d%%", total); + if (percent == 100) + percent = 99; + + sprintf (buf, "%d%%", percent); Dynarr_add_many (mode_spec_bufbyte_string, (Bufbyte *) buf, strlen (buf)); @@ -6827,7 +6806,6 @@ { Bufpos toppos = marker_position (w->start[type]); Bufpos botpos = BUF_Z (b) - w->window_end_pos[type]; - Charcount total = BUF_ZV (b) - BUF_BEGV (b); /* botpos is only accurate as of the last redisplay, so we can only treat it as a hint. In particular, after erase-buffer, @@ -6847,18 +6825,23 @@ /* This hard limit is ok since the string it will hold has a fixed maximum length of around 6. But just to be safe... */ char buf[10]; - - total = ((botpos - BUF_BEGV (b)) * 100 + total - 1) / total; + Charcount chars = botpos - BUF_BEGV (b); + Charcount total = BUF_ZV (b) - BUF_BEGV (b); + + /* Avoid overflow on big buffers */ + int percent = total > LONG_MAX/200 ? + (chars + total/200) / (total / 100) : + (chars * 100 + total/2) / max (total, 1); /* We can't normally display a 3-digit number, so get us a 2-digit number that is close. */ - if (total == 100) - total = 99; + if (percent == 100) + percent = 99; if (toppos <= BUF_BEGV (b)) - sprintf (buf, "Top%2d%%", total); + sprintf (buf, "Top%d%%", percent); else - sprintf (buf, "%2d%%", total); + sprintf (buf, "%d%%", percent); Dynarr_add_many (mode_spec_bufbyte_string, (Bufbyte *) buf, strlen (buf)); @@ -6961,7 +6944,7 @@ /* Given an array of display lines, free them and all data structures contained within them. */ -static void +void free_display_lines (display_line_dynarr *dla) { int line; @@ -6994,7 +6977,7 @@ static void -mark_glyph_block_dynarr (glyph_block_dynarr *gba, void (*markobj) (Lisp_Object)) +mark_glyph_block_dynarr (glyph_block_dynarr *gba) { if (gba) { @@ -7004,15 +6987,15 @@ for (; gb < gb_last; gb++) { if (!NILP (gb->glyph)) - markobj (gb->glyph); + mark_object (gb->glyph); if (!NILP (gb->extent)) - markobj (gb->extent); + mark_object (gb->extent); } } } static void -mark_redisplay_structs (display_line_dynarr *dla, void (*markobj) (Lisp_Object)) +mark_redisplay_structs (display_line_dynarr *dla) { display_line *dl = Dynarr_atp (dla, 0); display_line *dl_last = Dynarr_atp (dla, Dynarr_length (dla)); @@ -7034,35 +7017,35 @@ if (r->type == RUNE_DGLYPH) { if (!NILP (r->object.dglyph.glyph)) - markobj (r->object.dglyph.glyph); + mark_object (r->object.dglyph.glyph); if (!NILP (r->object.dglyph.extent)) - markobj (r->object.dglyph.extent); + mark_object (r->object.dglyph.extent); } } } - mark_glyph_block_dynarr (dl->left_glyphs, markobj); - mark_glyph_block_dynarr (dl->right_glyphs, markobj); + mark_glyph_block_dynarr (dl->left_glyphs); + mark_glyph_block_dynarr (dl->right_glyphs); } } static void -mark_window_mirror (struct window_mirror *mir, void (*markobj)(Lisp_Object)) -{ - mark_redisplay_structs (mir->current_display_lines, markobj); - mark_redisplay_structs (mir->desired_display_lines, markobj); +mark_window_mirror (struct window_mirror *mir) +{ + mark_redisplay_structs (mir->current_display_lines); + mark_redisplay_structs (mir->desired_display_lines); if (mir->next) - mark_window_mirror (mir->next, markobj); + mark_window_mirror (mir->next); if (mir->hchild) - mark_window_mirror (mir->hchild, markobj); + mark_window_mirror (mir->hchild); else if (mir->vchild) - mark_window_mirror (mir->vchild, markobj); + mark_window_mirror (mir->vchild); } void -mark_redisplay (void (*markobj)(Lisp_Object)) +mark_redisplay (void) { Lisp_Object frmcons, devcons, concons; @@ -7070,7 +7053,7 @@ { struct frame *f = XFRAME (XCAR (frmcons)); update_frame_window_mirror (f); - mark_window_mirror (f->root_mirror, markobj); + mark_window_mirror (f->root_mirror); } } @@ -7134,7 +7117,7 @@ /* This will get used quite a bit so we don't want to be constantly allocating and freeing it. */ -line_start_cache_dynarr *internal_cache; +static line_start_cache_dynarr *internal_cache; /* Makes internal_cache represent the TYPE display structs and only the TYPE display structs. */ @@ -7653,7 +7636,7 @@ } cur_elt--; - if (cur_elt < 0) + while (cur_elt < 0) { Bufpos from, to; int win_char_height; @@ -7673,7 +7656,20 @@ update_line_start_cache (w, from, to, point, 0); cur_elt = point_in_line_start_cache (w, cur_pos, 2) - 1; - assert (cur_elt >= 0); + assert (cur_elt >= -1); + /* This used to be cur_elt>=0 under the assumption that if + point is in the top line and not at BUF_BEGV, then + setting the window_start to a newline before the start of + the first line will always cause scrolling. + + However in my (jv) opinion this is wrong. That new line + can be hidden in various ways: invisible extents, an + explicit window-start not at a newline character etc. + The existence of those are indeed known to create crashes + on that assert. So we have no option but to continue the + search if we found point at the top of the line_start_cache + again. */ + cur_pos = Dynarr_atp (w->line_start_cache,0)->start; } prev_pos = cur_pos; } @@ -8969,6 +8965,8 @@ return 0; } +/* This is called if the built-in glyphs have their properties + changed. */ void redisplay_glyph_changed (Lisp_Object glyph, Lisp_Object property, Lisp_Object locale) @@ -9091,7 +9089,9 @@ preemption_count = 0; max_preempts = INIT_MAX_PREEMPTS; +#ifndef PDUMP if (!initialized) +#endif { cmotion_display_lines = Dynarr_new (display_line); mode_spec_bufbyte_string = Dynarr_new (Bufbyte); @@ -9171,7 +9171,6 @@ #endif /* INHIBIT_REDISPLAY_HOOKS */ defsymbol (&Qdisplay_warning_buffer, "display-warning-buffer"); defsymbol (&Qbar_cursor, "bar-cursor"); - defsymbol (&Qwindow_scroll_functions, "window-scroll-functions"); defsymbol (&Qredisplay_end_trigger_functions, "redisplay-end-trigger-functions"); @@ -9185,8 +9184,16 @@ } void +reinit_vars_of_redisplay (void) +{ + updating_line_start_cache = 0; +} + +void vars_of_redisplay (void) { + reinit_vars_of_redisplay (); + #if 0 staticpro (&last_arrow_position); staticpro (&last_arrow_string); @@ -9194,8 +9201,6 @@ last_arrow_string = Qnil; #endif /* 0 */ - updating_line_start_cache = 0; - /* #### Probably temporary */ DEFVAR_INT ("redisplay-cache-adjustment", &cache_adjustment /* \(Temporary) Setting this will impact the performance of the internal @@ -9280,7 +9285,7 @@ Vwindow_system = Qnil; /* #### Temporary shit until window-system is eliminated. */ - DEFVAR_LISP ("initial-window-system", &Vinitial_window_system /* + DEFVAR_CONST_LISP ("initial-window-system", &Vinitial_window_system /* DON'T TOUCH */ ); Vinitial_window_system = Qnil; diff -r 28d9c139be4c -r 11054d720c21 src/redisplay.h --- a/src/redisplay.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/redisplay.h Mon Aug 13 11:26:11 2007 +0200 @@ -145,8 +145,8 @@ /* HLINE */ struct { - int thickness; /* how thick to make hline */ - int yoffset; /* how far down from top of line to put top */ + short thickness; /* how thick to make hline */ + short yoffset; /* how far down from top of line to put top */ } hline; } object; /* actual rune object */ }; @@ -273,6 +273,8 @@ pixel-row itself, I think. */ unsigned short clip; /* amount of bottom of line to clip in pixels.*/ + unsigned short top_clip; /* amount of top of line to clip + in pixels.*/ Bufpos bufpos; /* first buffer position on line */ Bufpos end_bufpos; /* last buffer position on line */ Charcount offset; /* adjustment to bufpos vals */ @@ -301,15 +303,45 @@ }; #define DISPLAY_LINE_HEIGHT(dl) \ -(dl->ascent + dl->descent - dl->clip) +(dl->ascent + dl->descent - (dl->clip + dl->top_clip)) #define DISPLAY_LINE_YPOS(dl) \ -(dl->ypos - dl->ascent) +(dl->ypos - (dl->ascent - dl->top_clip)) +#define DISPLAY_LINE_YEND(dl) \ +((dl->ypos + dl->descent) - dl->clip) typedef struct { Dynarr_declare (display_line); } display_line_dynarr; +/* The following two structures are used to represent an area to +displayed and where to display it. Using these two structures all +combinations of clipping and position can be accommodated. */ + +/* This represents an area to be displayed into. */ +typedef struct display_box display_box; +struct display_box +{ + int xpos; /* absolute horizontal position of area */ + int ypos; /* absolute vertical position of area */ + int width, height; +}; + +/* This represents the area from a glyph to be displayed. */ +typedef struct display_glyph_area display_glyph_area; +struct display_glyph_area +{ + int xoffset; /* horizontal offset of the glyph, +ve means + display the glyph with x offset by xoffset, + -ve means display starting xoffset into the + glyph. */ + int yoffset; /* vertical offset of the glyph, +ve means + display the glyph with y offset by yoffset, + -ve means display starting xoffset into the + glyph. */ + int width, height; /* width and height of glyph to display. */ +}; + /* It could be argued that the following two structs belong in extents.h, but they're only used by redisplay and it simplifies the header files to put them here. */ @@ -345,6 +377,12 @@ unsigned int invisible_ellipses_already_displayed:1; }; +#define EDGE_TOP 1 +#define EDGE_LEFT 2 +#define EDGE_BOTTOM 4 +#define EDGE_RIGHT 8 +#define EDGE_ALL (EDGE_TOP | EDGE_LEFT | EDGE_BOTTOM | EDGE_RIGHT) + /*************************************************************************/ /* change flags */ @@ -390,6 +428,11 @@ extern int subwindows_changed; extern int subwindows_changed_set; +/* True if any displayed subwindow is in need of updating + somewhere. */ +extern int subwindows_state_changed; +extern int subwindows_state_changed_set; + /* True if an icon is in need of updating somewhere. */ extern int icon_changed; extern int icon_changed_set; @@ -463,23 +506,100 @@ #define MARK_GUTTER_CHANGED MARK_TYPE_CHANGED (gutter) #define MARK_GLYPHS_CHANGED MARK_TYPE_CHANGED (glyphs) #define MARK_SUBWINDOWS_CHANGED MARK_TYPE_CHANGED (subwindows) +#define MARK_SUBWINDOWS_STATE_CHANGED MARK_TYPE_CHANGED (subwindows_state) + + +#define CLASS_RESET_CHANGED_FLAGS(p) do { \ + (p)->buffers_changed = 0; \ + (p)->clip_changed = 0; \ + (p)->extents_changed = 0; \ + (p)->faces_changed = 0; \ + (p)->frame_changed = 0; \ + (p)->icon_changed = 0; \ + (p)->menubar_changed = 0; \ + (p)->modeline_changed = 0; \ + (p)->point_changed = 0; \ + (p)->toolbar_changed = 0; \ + (p)->gutter_changed = 0; \ + (p)->glyphs_changed = 0; \ + (p)->subwindows_changed = 0; \ + (p)->subwindows_state_changed = 0; \ + (p)->windows_changed = 0; \ + (p)->windows_structure_changed = 0; \ +} while (0) + +#define GLOBAL_RESET_CHANGED_FLAGS do { \ + buffers_changed = 0; \ + clip_changed = 0; \ + extents_changed = 0; \ + faces_changed = 0; \ + frame_changed = 0; \ + icon_changed = 0; \ + menubar_changed = 0; \ + modeline_changed = 0; \ + point_changed = 0; \ + toolbar_changed = 0; \ + gutter_changed = 0; \ + glyphs_changed = 0; \ + subwindows_changed = 0; \ + subwindows_state_changed = 0; \ + windows_changed = 0; \ + windows_structure_changed = 0; \ +} while (0) + +#define CLASS_REDISPLAY_FLAGS_CHANGEDP(p) \ + ( (p)->buffers_changed || \ + (p)->clip_changed || \ + (p)->extents_changed || \ + (p)->faces_changed || \ + (p)->frame_changed || \ + (p)->icon_changed || \ + (p)->menubar_changed || \ + (p)->modeline_changed || \ + (p)->point_changed || \ + (p)->toolbar_changed || \ + (p)->gutter_changed || \ + (p)->glyphs_changed || \ + (p)->subwindows_changed || \ + (p)->subwindows_state_changed || \ + (p)->windows_changed || \ + (p)->windows_structure_changed ) + +#define GLOBAL_REDISPLAY_FLAGS_CHANGEDP \ + ( buffers_changed || \ + clip_changed || \ + extents_changed || \ + faces_changed || \ + frame_changed || \ + icon_changed || \ + menubar_changed || \ + modeline_changed || \ + point_changed || \ + toolbar_changed || \ + gutter_changed || \ + glyphs_changed || \ + subwindows_changed || \ + subwindows_state_changed || \ + windows_changed || \ + windows_structure_changed ) + /* Anytime a console, device or frame is added or deleted we need to reset these flags. */ -#define RESET_CHANGED_SET_FLAGS \ - do { \ - buffers_changed_set = 0; \ - clip_changed_set = 0; \ - extents_changed_set = 0; \ - icon_changed_set = 0; \ - menubar_changed_set = 0; \ - modeline_changed_set = 0; \ - point_changed_set = 0; \ - toolbar_changed_set = 0; \ - gutter_changed_set = 0; \ - glyphs_changed_set = 0; \ - subwindows_changed_set = 0; \ - } while (0) +#define RESET_CHANGED_SET_FLAGS do { \ + buffers_changed_set = 0; \ + clip_changed_set = 0; \ + extents_changed_set = 0; \ + icon_changed_set = 0; \ + menubar_changed_set = 0; \ + modeline_changed_set = 0; \ + point_changed_set = 0; \ + toolbar_changed_set = 0; \ + gutter_changed_set = 0; \ + glyphs_changed_set = 0; \ + subwindows_changed_set = 0; \ + subwindows_state_changed_set = 0; \ +} while (0) /*************************************************************************/ @@ -555,6 +675,7 @@ int window_half_pixpos (struct window *w); void redisplay_echo_area (void); void free_display_structs (struct window_mirror *mir); +void free_display_lines (display_line_dynarr *dla); Bufbyte *generate_formatted_string (struct window *w, Lisp_Object format_str, Lisp_Object result_str, face_index findex, int type); @@ -571,7 +692,7 @@ Lisp_Object *obj1, Lisp_Object *obj2); void glyph_to_pixel_translation (struct window *w, int char_x, int char_y, int *pix_x, int *pix_y); -void mark_redisplay (void (*) (Lisp_Object)); +void mark_redisplay (void); int point_in_line_start_cache (struct window *w, Bufpos point, int min_past); int point_would_be_visible (struct window *w, Bufpos startp, @@ -599,12 +720,28 @@ int get_next_display_block (layout_bounds bounds, display_block_dynarr *dba, int start_pos, int *next_start); -void redisplay_output_subwindow (struct window *w, struct display_line *dl, - Lisp_Object image_instance, int xpos, - int xoffset, int start_pixpos, int width, - face_index findex, int cursor_start, - int cursor_width, int cursor_height); +void redisplay_output_layout (struct window *w, + Lisp_Object image_instance, + struct display_box* db, struct display_glyph_area* dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height); +void redisplay_output_subwindow (struct window *w, + Lisp_Object image_instance, + struct display_box* db, struct display_glyph_area* dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height); void redisplay_unmap_subwindows_maybe (struct frame* f, int x, int y, int width, int height); +void redisplay_output_pixmap (struct window *w, + Lisp_Object image_instance, + struct display_box* db, struct display_glyph_area* dga, + face_index findex, int cursor_start, int cursor_width, + int cursor_height, int offset_bitmap); +int redisplay_calculate_display_boxes (struct display_line *dl, int xpos, + int xoffset, int start_pixpos, int width, + struct display_box* dest, + struct display_glyph_area* src); +int redisplay_normalize_glyph_area (struct display_box* dest, + struct display_glyph_area* glyphsrc); void redisplay_clear_to_window_end (struct window *w, int ypos1, int ypos2); void redisplay_clear_region (Lisp_Object window, face_index findex, int x, int y, int width, int height); @@ -614,6 +751,7 @@ void redisplay_update_line (struct window *w, int first_line, int last_line, int update_values); void redisplay_output_window (struct window *w); +void bevel_modeline (struct window *w, struct display_line *dl); int redisplay_move_cursor (struct window *w, Bufpos new_point, int no_output_end); void redisplay_redraw_cursor (struct frame *f, int run_begin_end_meths); diff -r 28d9c139be4c -r 11054d720c21 src/s/cygwin32.h --- a/src/s/cygwin32.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/s/cygwin32.h Mon Aug 13 11:26:11 2007 +0200 @@ -105,6 +105,19 @@ #endif #endif +#ifndef SPI_GETWHEELSCROLLLINES +#define SPI_GETWHEELSCROLLLINES 104 +#endif +#ifndef WHEEL_PAGESCROLL +#define WHEEL_PAGESCROLL (UINT_MAX) +#endif +#ifndef WHEEL_DELTA +#define WHEEL_DELTA 120 +#endif +#ifndef WM_MOUSEWHEEL +#define WM_MOUSEWHEEL 0x20A +#endif + #define PBS_SMOOTH 0x01 #ifdef HAVE_MS_WINDOWS diff -r 28d9c139be4c -r 11054d720c21 src/s/mingw32.h --- a/src/s/mingw32.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/s/mingw32.h Mon Aug 13 11:26:11 2007 +0200 @@ -54,6 +54,19 @@ #define SHGFI_EXETYPE 0x2000 #define NSIG 23 +#ifndef SPI_GETWHEELSCROLLLINES +#define SPI_GETWHEELSCROLLLINES 104 +#endif +#ifndef WHEEL_PAGESCROLL +#define WHEEL_PAGESCROLL (UINT_MAX) +#endif +#ifndef WHEEL_DELTA +#define WHEEL_DELTA 120 +#endif +#ifndef WM_MOUSEWHEEL +#define WM_MOUSEWHEEL 0x20A +#endif + /* translate NT world unexec stuff to our a.out definitions */ #define strnicmp strncasecmp diff -r 28d9c139be4c -r 11054d720c21 src/s/windowsnt.h --- a/src/s/windowsnt.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/s/windowsnt.h Mon Aug 13 11:26:11 2007 +0200 @@ -370,3 +370,10 @@ #pragma data_seg("xdata") #pragma bss_seg("xdata") #endif + +#ifdef HAVE_SCROLLBARS +/* Ensure the NT 4 mouse definitions in winuser.h are available */ + #ifndef _WIN32_WINNT + #define _WIN32_WINNT 0x0400 + #endif +#endif diff -r 28d9c139be4c -r 11054d720c21 src/scrollbar-msw.c --- a/src/scrollbar-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/scrollbar-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -24,6 +24,7 @@ /* Synched up with: Not in FSF. */ #include +#include #include "lisp.h" #include "console-msw.h" @@ -265,6 +266,69 @@ } } +static int +can_scroll(struct scrollbar_instance* scrollbar) +{ + return scrollbar != NULL + && IsWindowVisible (SCROLLBAR_MSW_HANDLE (scrollbar)) + && IsWindowEnabled (SCROLLBAR_MSW_HANDLE (scrollbar)); +} + +int +mswindows_handle_mousewheel_event (Lisp_Object frame, int keys, int delta) +{ + int hasVertBar, hasHorzBar; /* Indicates prescence of scroll bars */ + unsigned wheelScrollLines = 0; /* Number of lines per wheel notch */ + + /* Find the currently selected window */ + Lisp_Object win = FRAME_SELECTED_WINDOW (XFRAME (frame)); + struct window* w = XWINDOW (win); + struct window_mirror* mirror = find_window_mirror (w); + + /* Check that there is something to scroll */ + hasVertBar = can_scroll (mirror->scrollbar_vertical_instance); + hasHorzBar = can_scroll (mirror->scrollbar_horizontal_instance); + if (!hasVertBar && !hasHorzBar) + return FALSE; + + /* No support for panning and zooming, so ignore */ + if (keys & (MK_SHIFT | MK_CONTROL)) + return FALSE; + + /* Get the number of lines per wheel delta */ + SystemParametersInfo (SPI_GETWHEELSCROLLLINES, 0, &wheelScrollLines, 0); + + /* Calculate the amount to scroll */ + if (wheelScrollLines == WHEEL_PAGESCROLL) + { + /* Scroll by a page */ + Lisp_Object function; + if (hasVertBar) + function = delta > 0 ? Qscrollbar_page_up : Qscrollbar_page_down; + else + function = delta > 0 ? Qscrollbar_page_left : Qscrollbar_page_right; + mswindows_enqueue_misc_user_event (frame, function, Fcons (win, Qnil)); + } + else /* Scroll by a number of lines */ + { + /* Calc the number of lines to scroll */ + int toScroll = MulDiv (delta, wheelScrollLines, WHEEL_DELTA); + + /* Do the scroll */ + Lisp_Object function; + if (hasVertBar) + function = delta > 0 ? Qscrollbar_line_up : Qscrollbar_line_down; + else + function = delta > 0 ? Qscrollbar_char_left : Qscrollbar_char_right; + if (toScroll < 0) + toScroll = -toScroll; + while (toScroll--) + mswindows_enqueue_misc_user_event (frame, function, win); + } + + return TRUE; +} + #ifdef MEMORY_USAGE_STATS static int diff -r 28d9c139be4c -r 11054d720c21 src/scrollbar-msw.h --- a/src/scrollbar-msw.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/scrollbar-msw.h Mon Aug 13 11:26:11 2007 +0200 @@ -57,6 +57,7 @@ */ void mswindows_handle_scrollbar_event (HWND hwnd, int code, int pos); +int mswindows_handle_mousewheel_event (Lisp_Object frame, int keys, int delta); #endif /* HAVE_MS_WINDOWS and HAVE_SCROLLBARS */ #endif /* _XEMACS_SCROLLBAR_MSW_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/scrollbar-x.c --- a/src/scrollbar-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/scrollbar-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -27,6 +27,7 @@ #include "lisp.h" #include "console-x.h" +#include "EmacsFrame.h" #include "glyphs-x.h" #include "gui-x.h" #include "scrollbar-x.h" @@ -672,19 +673,6 @@ 0, (Window) NULL); } -/* Called directly from x_any_window_to_frame in frame-x.c */ -EMACS_INT -x_window_is_scrollbar (struct frame *f, Window win) -{ - if (!FRAME_X_P (f)) - return 0; - - if (f->mirror_dirty) - update_frame_window_mirror (f); - return (EMACS_INT) x_scrollbar_loop (X_WINDOW_IS_SCROLLBAR, f->root_window, - f->root_mirror, 0, win); -} - /* Make sure that all scrollbars on frame are up-to-date. Called directly from x_set_frame_properties in frame-x.c*/ void @@ -745,8 +733,16 @@ } void +reinit_vars_of_scrollbar_x (void) +{ + stupid_vertical_scrollbar_drag_hack = 1; +} + +void vars_of_scrollbar_x (void) { + reinit_vars_of_scrollbar_x (); + #if defined (LWLIB_SCROLLBARS_LUCID) Fprovide (intern ("lucid-scrollbars")); #elif defined (LWLIB_SCROLLBARS_MOTIF) @@ -754,5 +750,4 @@ #elif defined (LWLIB_SCROLLBARS_ATHENA) Fprovide (intern ("athena-scrollbars")); #endif - stupid_vertical_scrollbar_drag_hack = 1; } diff -r 28d9c139be4c -r 11054d720c21 src/scrollbar-x.h --- a/src/scrollbar-x.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/scrollbar-x.h Mon Aug 13 11:26:11 2007 +0200 @@ -69,7 +69,6 @@ void x_update_frame_scrollbars (struct frame *f); void x_set_scrollbar_pointer (struct frame *f, Lisp_Object cursor); -EMACS_INT x_window_is_scrollbar (struct frame *f, Window win); #endif /* HAVE_X_WINDOWS and HAVE_SCROLLBARS */ #endif /* _XEMACS_SCROLLBAR_H_ */ diff -r 28d9c139be4c -r 11054d720c21 src/search.c --- a/src/search.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/search.c Mon Aug 13 11:26:11 2007 +0200 @@ -54,10 +54,10 @@ }; /* The instances of that struct. */ -struct regexp_cache searchbufs[REGEXP_CACHE_SIZE]; +static struct regexp_cache searchbufs[REGEXP_CACHE_SIZE]; /* The head of the linked list; points to the most recently used buffer. */ -struct regexp_cache *searchbuf_head; +static struct regexp_cache *searchbuf_head; /* Every call to re_match, etc., must pass &search_regs as the regs @@ -2574,9 +2574,12 @@ } void -vars_of_search (void) +reinit_vars_of_search (void) { - REGISTER int i; + int i; + + last_thing_searched = Qnil; + staticpro_nodump (&last_thing_searched); for (i = 0; i < REGEXP_CACHE_SIZE; ++i) { @@ -2584,13 +2587,16 @@ searchbufs[i].buf.buffer = (unsigned char *) xmalloc (100); searchbufs[i].buf.fastmap = searchbufs[i].fastmap; searchbufs[i].regexp = Qnil; - staticpro (&searchbufs[i].regexp); + staticpro_nodump (&searchbufs[i].regexp); searchbufs[i].next = (i == REGEXP_CACHE_SIZE-1 ? 0 : &searchbufs[i+1]); } searchbuf_head = &searchbufs[0]; +} - last_thing_searched = Qnil; - staticpro (&last_thing_searched); +void +vars_of_search (void) +{ + reinit_vars_of_search (); DEFVAR_LISP ("forward-word-regexp", &Vforward_word_regexp /* *Regular expression to be used in `forward-word'. diff -r 28d9c139be4c -r 11054d720c21 src/select-x.c --- a/src/select-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/select-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -1492,15 +1492,18 @@ cut_buffers_initialized = 1; } -#define CHECK_CUTBUFFER(symbol) \ - { CHECK_SYMBOL (symbol); \ - if (!EQ((symbol),QCUT_BUFFER0) && !EQ((symbol),QCUT_BUFFER1) && \ - !EQ((symbol),QCUT_BUFFER2) && !EQ((symbol),QCUT_BUFFER3) && \ - !EQ((symbol),QCUT_BUFFER4) && !EQ((symbol),QCUT_BUFFER5) && \ - !EQ((symbol),QCUT_BUFFER6) && !EQ((symbol),QCUT_BUFFER7)) \ - signal_error (Qerror, list2 (build_string ("Doesn't name a cutbuffer"), \ - (symbol))); \ - } +#define CHECK_CUTBUFFER(symbol) do { \ + CHECK_SYMBOL (symbol); \ + if (! (EQ (symbol, QCUT_BUFFER0) || \ + EQ (symbol, QCUT_BUFFER1) || \ + EQ (symbol, QCUT_BUFFER2) || \ + EQ (symbol, QCUT_BUFFER3) || \ + EQ (symbol, QCUT_BUFFER4) || \ + EQ (symbol, QCUT_BUFFER5) || \ + EQ (symbol, QCUT_BUFFER6) || \ + EQ (symbol, QCUT_BUFFER7))) \ + signal_simple_error ("Doesn't name a cutbuffer", symbol); \ +} while (0) DEFUN ("x-get-cutbuffer-internal", Fx_get_cutbuffer_internal, 1, 1, 0, /* Return the value of the named CUTBUFFER (typically CUT_BUFFER0). @@ -1694,18 +1697,24 @@ } void -vars_of_xselect (void) +reinit_vars_of_xselect (void) { -#ifdef CUT_BUFFER_SUPPORT - cut_buffers_initialized = 0; - Fprovide (intern ("cut-buffer")); -#endif - reading_selection_reply = 0; reading_which_selection = 0; selection_reply_timed_out = 0; for_whom_the_bell_tolls = 0; prop_location_tick = 0; +} + +void +vars_of_xselect (void) +{ + reinit_vars_of_xselect (); + +#ifdef CUT_BUFFER_SUPPORT + cut_buffers_initialized = 0; + Fprovide (intern ("cut-buffer")); +#endif DEFVAR_LISP ("x-sent-selection-hooks", &Vx_sent_selection_hooks /* A function or functions to be called after we have responded to some diff -r 28d9c139be4c -r 11054d720c21 src/sound.c --- a/src/sound.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/sound.c Mon Aug 13 11:26:11 2007 +0200 @@ -25,6 +25,7 @@ Hacked on quite a bit by various others. */ #include +#include #include "lisp.h" #include "buffer.h" @@ -45,6 +46,7 @@ #endif int bell_volume; +int bell_inhibit_time; Lisp_Object Vsound_alist; Lisp_Object Vsynchronous_sounds; Lisp_Object Vnative_sound_only_on_console; @@ -347,25 +349,28 @@ */ (arg, sound, device)) { - struct device *d = decode_device (device); + static time_t last_bell_time = (time_t) 0; + static struct device *last_bell_device = (struct device*) 0; + time_t now; + struct device *d = decode_device (device); XSETDEVICE (device, d); + now = time (0); - /* #### This is utterly disgusting, and is probably a remnant from - legacy code that used `ding'+`message' to signal error instead - calling `error'. As a result, there is no way to beep from Lisp - directly, without also invoking this aspect. Maybe we should - define a `ring-bell' function that simply beeps on the console, - which `ding' should invoke? --hniksic */ if (NILP (arg) && !NILP (Vexecuting_macro)) /* Stop executing a keyboard macro. */ error ("Keyboard macro terminated by a command ringing the bell"); + + if (d == last_bell_device && now-last_bell_time < bell_inhibit_time) + return Qnil; else if (visible_bell && DEVMETH (d, flash, (d))) ; else Fplay_sound (sound, Qnil, device); - - return Qnil; + + last_bell_time = now; + last_bell_device = d; + return Qnil; } DEFUN ("wait-for-sounds", Fwait_for_sounds, 0, 1, 0, /* @@ -532,6 +537,11 @@ *How loud to be, from 0 to 100. */ ); bell_volume = 50; + + DEFVAR_INT ("bell-inhibit-time", &bell_inhibit_time /* +*Don't ring the bell on the same device more than once within this many seconds. +*/ ); + bell_inhibit_time = 0; DEFVAR_LISP ("sound-alist", &Vsound_alist /* An alist associating names with sounds. @@ -559,8 +569,8 @@ load-sound-file. Caveats: - - You can only play audio data if running on the console screen of a - Sun SparcStation, SGI, or HP9000s700. + - XEmacs must be built with sound support for your system. Not all + systems support sound. - The pitch, duration, and volume options are available everywhere, but many X servers ignore the `pitch' option. diff -r 28d9c139be4c -r 11054d720c21 src/specifier.c --- a/src/specifier.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/specifier.c Mon Aug 13 11:26:11 2007 +0200 @@ -64,7 +64,28 @@ Dynarr_declare (specifier_type_entry); } specifier_type_entry_dynarr; -specifier_type_entry_dynarr *the_specifier_type_entry_dynarr; +static specifier_type_entry_dynarr *the_specifier_type_entry_dynarr; + +static const struct lrecord_description ste_description_1[] = { + { XD_LISP_OBJECT, offsetof(specifier_type_entry, symbol), 1 }, + { XD_STRUCT_PTR, offsetof(specifier_type_entry, meths), 1, &specifier_methods_description }, + { XD_END } +}; + +static const struct struct_description ste_description = { + sizeof(specifier_type_entry), + ste_description_1 +}; + +static const struct lrecord_description sted_description_1[] = { + XD_DYNARR_DESC(specifier_type_entry_dynarr, &ste_description), + { XD_END } +}; + +static const struct struct_description sted_description = { + sizeof(specifier_type_entry_dynarr), + sted_description_1 +}; static Lisp_Object Vspecifier_type_list; @@ -180,19 +201,19 @@ } static Lisp_Object -mark_specifier (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_specifier (Lisp_Object obj) { struct Lisp_Specifier *specifier = XSPECIFIER (obj); - markobj (specifier->global_specs); - markobj (specifier->device_specs); - markobj (specifier->frame_specs); - markobj (specifier->window_specs); - markobj (specifier->buffer_specs); - markobj (specifier->magic_parent); - markobj (specifier->fallback); + mark_object (specifier->global_specs); + mark_object (specifier->device_specs); + mark_object (specifier->frame_specs); + mark_object (specifier->window_specs); + mark_object (specifier->buffer_specs); + mark_object (specifier->magic_parent); + mark_object (specifier->fallback); if (!GHOST_SPECIFIER_P (XSPECIFIER (obj))) - MAYBE_SPECMETH (specifier, mark, (obj, markobj)); + MAYBE_SPECMETH (specifier, mark, (obj)); return Qnil; } @@ -216,24 +237,24 @@ */ void -prune_specifiers (int (*obj_marked_p) (Lisp_Object)) +prune_specifiers (void) { Lisp_Object rest, prev = Qnil; for (rest = Vall_specifiers; - !GC_NILP (rest); + !NILP (rest); rest = XSPECIFIER (rest)->next_specifier) { - if (! obj_marked_p (rest)) + if (! marked_p (rest)) { struct Lisp_Specifier* sp = XSPECIFIER (rest); /* A bit of assertion that we're removing both parts of the magic one altogether */ - assert (!GC_MAGIC_SPECIFIER_P(sp) - || (GC_BODILY_SPECIFIER_P(sp) && obj_marked_p (sp->fallback)) - || (GC_GHOST_SPECIFIER_P(sp) && obj_marked_p (sp->magic_parent))); + assert (!MAGIC_SPECIFIER_P(sp) + || (BODILY_SPECIFIER_P(sp) && marked_p (sp->fallback)) + || (GHOST_SPECIFIER_P(sp) && marked_p (sp->magic_parent))); /* This specifier is garbage. Remove it from the list. */ - if (GC_NILP (prev)) + if (NILP (prev)) Vall_specifiers = sp->next_specifier; else XSPECIFIER (prev)->next_specifier = sp->next_specifier; @@ -280,7 +301,7 @@ { struct Lisp_Specifier *sp = (struct Lisp_Specifier *) header; /* don't be snafued by the disksave finalization. */ - if (!for_disksave && !GC_GHOST_SPECIFIER_P(sp) && sp->caching) + if (!for_disksave && !GHOST_SPECIFIER_P(sp) && sp->caching) { xfree (sp->caching); sp->caching = 0; @@ -336,18 +357,51 @@ sizeof_specifier (CONST void *header) { if (GHOST_SPECIFIER_P ((struct Lisp_Specifier *) header)) - return sizeof (struct Lisp_Specifier); + return offsetof (struct Lisp_Specifier, data); else { CONST struct Lisp_Specifier *p = (CONST struct Lisp_Specifier *) header; - return sizeof (*p) + p->methods->extra_data_size - 1; + return offsetof (struct Lisp_Specifier, data) + p->methods->extra_data_size; } } +static const struct lrecord_description specifier_methods_description_1[] = { + { XD_LISP_OBJECT, offsetof(struct specifier_methods, predicate_symbol), 1 }, + { XD_END } +}; + +const struct struct_description specifier_methods_description = { + sizeof(struct specifier_methods), + specifier_methods_description_1 +}; + +static const struct lrecord_description specifier_caching_description_1[] = { + { XD_END } +}; + +static const struct struct_description specifier_caching_description = { + sizeof(struct specifier_caching), + specifier_caching_description_1 +}; + +static const struct lrecord_description specifier_description[] = { + { XD_STRUCT_PTR, offsetof(struct Lisp_Specifier, methods), 1, &specifier_methods_description }, + { XD_LO_LINK, offsetof(struct Lisp_Specifier, next_specifier) }, + { XD_LISP_OBJECT, offsetof(struct Lisp_Specifier, global_specs), 5 }, + { XD_STRUCT_PTR, offsetof(struct Lisp_Specifier, caching), 1, &specifier_caching_description }, + { XD_LISP_OBJECT, offsetof(struct Lisp_Specifier, magic_parent), 2 }, + { XD_SPECIFIER_END } +}; + +const struct lrecord_description specifier_empty_extra_description[] = { + { XD_END } +}; + DEFINE_LRECORD_SEQUENCE_IMPLEMENTATION ("specifier", specifier, mark_specifier, print_specifier, finalize_specifier, - specifier_equal, specifier_hash, 0, + specifier_equal, specifier_hash, + specifier_description, sizeof_specifier, struct Lisp_Specifier); @@ -414,8 +468,8 @@ { Lisp_Object specifier; struct Lisp_Specifier *sp = (struct Lisp_Specifier *) - alloc_lcrecord (sizeof (struct Lisp_Specifier) + - data_size - 1, &lrecord_specifier); + alloc_lcrecord (offsetof (struct Lisp_Specifier, data) + + data_size, &lrecord_specifier); sp->methods = spec_meths; sp->global_specs = Qnil; @@ -3125,6 +3179,7 @@ specifier_type_create (void) { the_specifier_type_entry_dynarr = Dynarr_new (specifier_type_entry); + dumpstruct (&the_specifier_type_entry_dynarr, &sted_description); Vspecifier_type_list = Qnil; staticpro (&Vspecifier_type_list); @@ -3149,6 +3204,16 @@ } void +reinit_specifier_type_create (void) +{ + REINITIALIZE_SPECIFIER_TYPE (generic); + REINITIALIZE_SPECIFIER_TYPE (integer); + REINITIALIZE_SPECIFIER_TYPE (natnum); + REINITIALIZE_SPECIFIER_TYPE (boolean); + REINITIALIZE_SPECIFIER_TYPE (display_table); +} + +void vars_of_specifier (void) { Vcached_specifiers = Qnil; @@ -3157,6 +3222,7 @@ /* Do NOT mark through this, or specifiers will never be GC'd. This is the same deal as for weak hash tables. */ Vall_specifiers = Qnil; + pdump_wire_list (&Vall_specifiers); Vuser_defined_tags = Qnil; staticpro (&Vuser_defined_tags); diff -r 28d9c139be4c -r 11054d720c21 src/specifier.h --- a/src/specifier.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/specifier.h Mon Aug 13 11:26:11 2007 +0200 @@ -83,6 +83,8 @@ same time. */ +extern const struct struct_description specifier_methods_description; + struct specifier_methods { CONST char *name; @@ -95,7 +97,7 @@ /* Mark method: Mark any lisp object within specifier data structure. Not required if no specifier data are Lisp_Objects. */ - void (*mark_method) (Lisp_Object specifier, void (*markobj) (Lisp_Object)); + void (*mark_method) (Lisp_Object specifier); /* Equal method: Compare two specifiers. This is called after ensuring that the two specifiers are of the same type, and have @@ -185,6 +187,7 @@ void (*after_change_method) (Lisp_Object specifier, Lisp_Object locale); + const struct lrecord_description *extra_description; int extra_data_size; }; @@ -232,7 +235,6 @@ #define XSPECIFIER(x) XRECORD (x, specifier, struct Lisp_Specifier) #define XSETSPECIFIER(x, p) XSETRECORD (x, p, specifier) #define SPECIFIERP(x) RECORDP (x, specifier) -#define GC_SPECIFIERP(x) GC_RECORDP (x, specifier) #define CHECK_SPECIFIER(x) CHECK_RECORD (x, specifier) #define CONCHECK_SPECIFIER(x) CONCHECK_RECORD (x, specifier) @@ -251,6 +253,9 @@ /***** Defining new specifier types *****/ +#define specifier_data_offset (offsetof(struct Lisp_Specifier, data)) +extern const struct lrecord_description specifier_empty_extra_description[]; + #ifdef ERROR_CHECK_TYPECHECK #define DECLARE_SPECIFIER_TYPE(type) \ extern struct specifier_methods * type##_specifier_methods; \ @@ -279,10 +284,17 @@ struct specifier_methods * type##_specifier_methods #define INITIALIZE_SPECIFIER_TYPE(type, obj_name, pred_sym) do { \ - type##_specifier_methods = xnew_and_zero (struct specifier_methods); \ - type##_specifier_methods->name = obj_name; \ - defsymbol (&type##_specifier_methods->predicate_symbol, pred_sym); \ - add_entry_to_specifier_type_list (Q##type, type##_specifier_methods); \ + type##_specifier_methods = xnew_and_zero (struct specifier_methods); \ + type##_specifier_methods->name = obj_name; \ + type##_specifier_methods->extra_description = \ + specifier_empty_extra_description; \ + defsymbol_nodump (&type##_specifier_methods->predicate_symbol, pred_sym); \ + add_entry_to_specifier_type_list (Q##type, type##_specifier_methods); \ + dumpstruct (&type##_specifier_methods, &specifier_methods_description); \ +} while (0) + +#define REINITIALIZE_SPECIFIER_TYPE(type) do { \ + staticpro_nodump (&type##_specifier_methods->predicate_symbol); \ } while (0) #define INITIALIZE_SPECIFIER_TYPE_WITH_DATA(type, obj_name, pred_sym) \ @@ -290,6 +302,8 @@ INITIALIZE_SPECIFIER_TYPE (type, obj_name, pred_sym); \ type##_specifier_methods->extra_data_size = \ sizeof (struct type##_specifier); \ + type##_specifier_methods->extra_description = \ + type##_specifier_description; \ } while (0) /* Declare that specifier-type TYPE has method METH; used in @@ -303,24 +317,13 @@ ((sp)->methods == type##_specifier_methods) /* Any of the two of the magic spec */ -#define MAGIC_SPECIFIER_P(sp) \ - (!NILP((sp)->magic_parent)) +#define MAGIC_SPECIFIER_P(sp) (!NILP((sp)->magic_parent)) /* Normal part of the magic specifier */ -#define BODILY_SPECIFIER_P(sp) \ - (EQ ((sp)->magic_parent, Qt)) +#define BODILY_SPECIFIER_P(sp) EQ ((sp)->magic_parent, Qt) /* Ghost part of the magic specifier */ -#define GHOST_SPECIFIER_P(sp) \ - (SPECIFIERP((sp)->magic_parent)) -/* The same three, when used in GC */ -#define GC_MAGIC_SPECIFIER_P(sp) \ - (!GC_NILP((sp)->magic_parent)) -#define GC_BODILY_SPECIFIER_P(sp) \ - (GC_EQ ((sp)->magic_parent, Qt)) -#define GC_GHOST_SPECIFIER_P(sp) \ - (GC_SPECIFIERP((sp)->magic_parent)) +#define GHOST_SPECIFIER_P(sp) SPECIFIERP((sp)->magic_parent) -#define GHOST_SPECIFIER(sp) \ - (XSPECIFIER ((sp)->fallback)) +#define GHOST_SPECIFIER(sp) XSPECIFIER ((sp)->fallback) #ifdef ERROR_CHECK_TYPECHECK # define SPECIFIER_TYPE_DATA(sp, type) \ @@ -425,7 +428,7 @@ int unlock_ghost_specifiers_protected (void); void cleanup_specifiers (void); -void prune_specifiers (int (*obj_marked_p) (Lisp_Object)); +void prune_specifiers (void); void setup_device_initial_specifier_tags (struct device *d); void kill_specifier_buffer_locals (Lisp_Object buffer); diff -r 28d9c139be4c -r 11054d720c21 src/symbols.c --- a/src/symbols.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/symbols.c Mon Aug 13 11:26:11 2007 +0200 @@ -63,7 +63,7 @@ Lisp_Object Qget_value, Qset_value, Qbound_predicate, Qmake_unbound; Lisp_Object Qlocal_predicate, Qmake_local; -Lisp_Object Qboundp, Qfboundp, Qglobally_boundp, Qmakunbound; +Lisp_Object Qboundp, Qglobally_boundp, Qmakunbound; Lisp_Object Qsymbol_value, Qset, Qdefault_boundp, Qdefault_value; Lisp_Object Qset_default, Qsetq_default; Lisp_Object Qmake_variable_buffer_local, Qmake_local_variable; @@ -87,20 +87,20 @@ static Lisp_Object -mark_symbol (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_symbol (Lisp_Object obj) { struct Lisp_Symbol *sym = XSYMBOL (obj); Lisp_Object pname; - markobj (sym->value); - markobj (sym->function); + mark_object (sym->value); + mark_object (sym->function); XSETSTRING (pname, sym->name); - markobj (pname); + mark_object (pname); if (!symbol_next (sym)) return sym->plist; else { - markobj (sym->plist); + mark_object (sym->plist); /* Mark the rest of the symbols in the obarray hash-chain */ sym = symbol_next (sym); XSETSYMBOL (obj, sym); @@ -109,7 +109,8 @@ } static const struct lrecord_description symbol_description[] = { - { XD_LISP_OBJECT, offsetof(struct Lisp_Symbol, next), 5 } + { XD_LISP_OBJECT, offsetof(struct Lisp_Symbol, next), 5 }, + { XD_END } }; DEFINE_BASIC_LRECORD_IMPLEMENTATION ("symbol", symbol, @@ -895,8 +896,7 @@ symbol to operate on. */ static Lisp_Object -mark_symbol_value_buffer_local (Lisp_Object obj, - void (*markobj) (Lisp_Object)) +mark_symbol_value_buffer_local (Lisp_Object obj) { struct symbol_value_buffer_local *bfwd; @@ -906,15 +906,14 @@ #endif bfwd = XSYMBOL_VALUE_BUFFER_LOCAL (obj); - markobj (bfwd->default_value); - markobj (bfwd->current_value); - markobj (bfwd->current_buffer); + mark_object (bfwd->default_value); + mark_object (bfwd->current_value); + mark_object (bfwd->current_buffer); return bfwd->current_alist_element; } static Lisp_Object -mark_symbol_value_lisp_magic (Lisp_Object obj, - void (*markobj) (Lisp_Object)) +mark_symbol_value_lisp_magic (Lisp_Object obj) { struct symbol_value_lisp_magic *bfwd; int i; @@ -924,22 +923,21 @@ bfwd = XSYMBOL_VALUE_LISP_MAGIC (obj); for (i = 0; i < MAGIC_HANDLER_MAX; i++) { - markobj (bfwd->handler[i]); - markobj (bfwd->harg[i]); + mark_object (bfwd->handler[i]); + mark_object (bfwd->harg[i]); } return bfwd->shadowed; } static Lisp_Object -mark_symbol_value_varalias (Lisp_Object obj, - void (*markobj) (Lisp_Object)) +mark_symbol_value_varalias (Lisp_Object obj) { struct symbol_value_varalias *bfwd; assert (XSYMBOL_VALUE_MAGIC_TYPE (obj) == SYMVAL_VARALIAS); bfwd = XSYMBOL_VALUE_VARALIAS (obj); - markobj (bfwd->shadowed); + mark_object (bfwd->shadowed); return bfwd->aliasee; } @@ -956,8 +954,13 @@ write_c_string (buf, printcharfun); } +static const struct lrecord_description symbol_value_forward_description[] = { + { XD_END } +}; + static const struct lrecord_description symbol_value_buffer_local_description[] = { - { XD_LISP_OBJECT, offsetof(struct symbol_value_buffer_local, default_value), 4 }, + { XD_LISP_OBJECT, offsetof(struct symbol_value_buffer_local, default_value), 1 }, + { XD_LO_RESET_NIL, offsetof(struct symbol_value_buffer_local, current_value), 3 }, { XD_END } }; @@ -974,7 +977,8 @@ DEFINE_LRECORD_IMPLEMENTATION ("symbol-value-forward", symbol_value_forward, this_one_is_unmarkable, - print_symbol_value_magic, 0, 0, 0, 0, + print_symbol_value_magic, 0, 0, 0, + symbol_value_forward_description, struct symbol_value_forward); DEFINE_LRECORD_IMPLEMENTATION ("symbol-value-buffer-local", @@ -1214,7 +1218,7 @@ if (magicfun) magicfun (sym, &newval, Qnil, 0); *((int *) symbol_value_forward_forward (fwd)) - = ((NILP (newval)) ? 0 : 1); + = !NILP (newval); return; case SYMVAL_OBJECT_FORWARD: @@ -1547,7 +1551,9 @@ /* This can also get called while we're preparing to shutdown. #### What should really happen in that case? Should we actually fix things so we can't get here in that case? */ +#ifndef PDUMP assert (!initialized || preparing_for_armageddon); +#endif con = 0; } @@ -1583,7 +1589,9 @@ /* This can also get called while we're preparing to shutdown. #### What should really happen in that case? Should we actually fix things so we can't get here in that case? */ +#ifndef PDUMP assert (!initialized || preparing_for_armageddon); +#endif con = 0; } @@ -3153,6 +3161,19 @@ defsymbol (&Qt, "t"); XSYMBOL (Qt)->value = Qt; /* Veritas aetera */ Vquit_flag = Qnil; + + pdump_wire (&Qnil); + pdump_wire (&Qunbound); + pdump_wire (&Vquit_flag); +} + +void +defsymbol_nodump (Lisp_Object *location, CONST char *name) +{ + *location = Fintern (make_string_nocopy ((CONST Bufbyte *) name, + strlen (name)), + Qnil); + staticpro_nodump (location); } void @@ -3268,11 +3289,11 @@ assert (SYMBOLP (inherits_from)); conds = Fget (inherits_from, Qerror_conditions, Qnil); - pure_put (*symbol, Qerror_conditions, Fcons (*symbol, conds)); + Fput (*symbol, Qerror_conditions, Fcons (*symbol, conds)); /* NOT build_translated_string (). This function is called at load time and the string needs to get translated at run time. (This happens in the function (display-error) in cmdloop.el.) */ - pure_put (*symbol, Qerror_message, build_string (messuhhj)); + Fput (*symbol, Qerror_message, build_string (messuhhj)); } void @@ -3291,7 +3312,6 @@ defsymbol (&Qmake_local, "make-local"); defsymbol (&Qboundp, "boundp"); - defsymbol (&Qfboundp, "fboundp"); defsymbol (&Qglobally_boundp, "globally-boundp"); defsymbol (&Qmakunbound, "makunbound"); defsymbol (&Qsymbol_value, "symbol-value"); diff -r 28d9c139be4c -r 11054d720c21 src/symeval.h --- a/src/symeval.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/symeval.h Mon Aug 13 11:26:11 2007 +0200 @@ -282,6 +282,7 @@ #define DEFSUBR_MACRO(Fname) defsubr_macro (&S##Fname) void defsymbol (Lisp_Object *location, CONST char *name); +void defsymbol_nodump (Lisp_Object *location, CONST char *name); void defkeyword (Lisp_Object *location, CONST char *name); diff -r 28d9c139be4c -r 11054d720c21 src/symsinit.h --- a/src/symsinit.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/symsinit.h Mon Aug 13 11:26:11 2007 +0200 @@ -33,11 +33,13 @@ void init_ralloc (void); void init_signals_very_early (void); -/* Early Lisp-engine initialization (dump-time only). */ +/* Early Lisp-engine initialization (dump-time for init, run-time for reinit). */ void init_alloc_once_early (void); +void reinit_alloc_once_early (void); void init_symbols_once_early (void); void init_errors_once_early (void); +void reinit_opaque_once_early (void); void init_opaque_once_early (void); /* Declare the built-in symbols and primitives (dump-time only). */ @@ -147,17 +149,21 @@ void syms_of_xselect (void); void syms_of_eldap (void); -/* Initialize the console types (dump-time only). */ +/* Initialize the console types (dump-time but for reinit_). */ void console_type_create (void); void console_type_create_stream (void); +void reinit_console_type_create_stream (void); void console_type_create_tty (void); +void reinit_console_type_create_tty (void); void console_type_create_device_tty (void); void console_type_create_frame_tty (void); void console_type_create_objects_tty (void); void console_type_create_redisplay_tty (void); void console_type_create_x (void); +void reinit_console_type_create_x (void); void console_type_create_device_x (void); +void reinit_console_type_create_device_x (void); void console_type_create_frame_x (void); void console_type_create_glyphs_x (void); void console_type_create_menubar_x (void); @@ -168,6 +174,7 @@ void console_type_create_toolbar_x (void); void console_type_create_dialog_x (void); void console_type_create_mswindows (void); +void reinit_console_type_create_mswindows (void); void console_type_create_device_mswindows (void); void console_type_create_frame_mswindows (void); void console_type_create_menubar_mswindows (void); @@ -182,10 +189,15 @@ /* Initialize the specifier types (dump-time only). */ void specifier_type_create (void); +void reinit_specifier_type_create (void); void specifier_type_create_image (void); +void reinit_specifier_type_create_image (void); void specifier_type_create_gutter (void); +void reinit_specifier_type_create_gutter (void); void specifier_type_create_objects (void); +void reinit_specifier_type_create_objects (void); void specifier_type_create_toolbar (void); +void reinit_specifier_type_create_toolbar (void); /* Initialize the structure types (dump-time only). */ @@ -220,12 +232,13 @@ void init_provide_once (void); -/* Initialize most variables (dump-time only). */ +/* Initialize most variables (dump-time for vars_, run-time for reinit_vars). */ void vars_of_abbrev (void); void vars_of_alloc (void); void vars_of_balloon_x (void); void vars_of_buffer (void); +void reinit_vars_of_buffer (void); void vars_of_bytecode (void); void vars_of_callint (void); void vars_of_callproc (void); @@ -233,15 +246,19 @@ void vars_of_cmdloop (void); void vars_of_cmds (void); void vars_of_console (void); +void reinit_vars_of_console (void); void vars_of_console_stream (void); void vars_of_console_mswindows (void); void vars_of_console_tty (void); void vars_of_data (void); void vars_of_database (void); void vars_of_debug (void); +void reinit_vars_of_debug (void); void vars_of_device (void); +void reinit_vars_of_device (void); void vars_of_device_mswindows (void); void vars_of_device_x (void); +void reinit_vars_of_device_x (void); void vars_of_dialog (void); void vars_of_dialog_x (void); void vars_of_dialog_mswindows (void); @@ -253,17 +270,25 @@ void vars_of_elhash (void); void vars_of_emacs (void); void vars_of_eval (void); +void reinit_vars_of_eval (void); void vars_of_event_stream (void); +void reinit_vars_of_event_stream (void); void vars_of_event_tty (void); +void reinit_vars_of_event_tty (void); void vars_of_event_mswindows (void); +void reinit_vars_of_event_mswindows (void); void vars_of_event_Xt (void); +void reinit_vars_of_event_Xt (void); void vars_of_events (void); +void reinit_vars_of_events (void); void vars_of_extents (void); +void reinit_vars_of_extents (void); void vars_of_faces (void); void vars_of_fileio (void); void vars_of_filelock (void); void vars_of_floatfns (void); void vars_of_font_lock (void); +void reinit_vars_of_font_lock (void); void vars_of_frame_tty (void); void vars_of_frame_mswindows (void); void vars_of_frame_x (void); @@ -271,26 +296,35 @@ void vars_of_glyphs_x (void); void vars_of_glyphs_eimage (void); void vars_of_glyphs_widget (void); +void reinit_vars_of_glyphs_widget (void); void vars_of_glyphs_mswindows (void); void vars_of_glyphs (void); +void reinit_vars_of_glyphs (void); void vars_of_gui_x (void); +void reinit_vars_of_gui_x (void); void vars_of_gui (void); void vars_of_gutter (void); void vars_of_input_method_motif (void); void vars_of_input_method_xlib (void); void vars_of_indent (void); void vars_of_insdel (void); +void reinit_vars_of_insdel (void); void vars_of_intl (void); void vars_of_keymap (void); void vars_of_lread (void); +void reinit_vars_of_lread (void); void vars_of_lstream (void); +void reinit_vars_of_lstream (void); void vars_of_macros (void); void vars_of_md5 (void); void vars_of_menubar_x (void); +void reinit_vars_of_menubar_x (void); void vars_of_menubar (void); void vars_of_menubar_mswindows (void); void vars_of_minibuf (void); +void reinit_vars_of_minibuf (void); void vars_of_module (void); +void reinit_vars_of_module (void); void vars_of_mule (void); void vars_of_mule_canna (void); void vars_of_mule_ccl(void); @@ -299,20 +333,25 @@ void vars_of_mule_wnn (void); void vars_of_ntproc (void); void vars_of_objects (void); +void reinit_vars_of_objects (void); void vars_of_objects_tty (void); void vars_of_objects_mswindows (void); void vars_of_objects_x (void); void vars_of_print (void); +void reinit_vars_of_print (void); void vars_of_process (void); void vars_of_process_nt (void); void vars_of_process_unix (void); void vars_of_profile (void); void vars_of_ralloc (void); void vars_of_redisplay (void); +void reinit_vars_of_redisplay (void); void vars_of_scrollbar_x (void); +void reinit_vars_of_scrollbar_x (void); void vars_of_scrollbar (void); void vars_of_scrollbar_mswindows (void); void vars_of_search (void); +void reinit_vars_of_search (void); void vars_of_select (void); void vars_of_select_mswindows (void); void vars_of_sound (void); @@ -323,8 +362,11 @@ void vars_of_toolbar (void); void vars_of_tooltalk (void); void vars_of_undo (void); +void reinit_vars_of_undo (void); void vars_of_window (void); +void reinit_vars_of_window (void); void vars_of_xselect (void); +void reinit_vars_of_xselect (void); void vars_of_eldap (void); /* Initialize specifier variables (dump-time only). */ @@ -338,7 +380,7 @@ void specifier_vars_of_window (void); /* Initialize variables with complex dependencies - on other variables (dump-time only). */ + on other variables (dump-time for complex_vars_, run-time for reinit_). */ void complex_vars_of_regex (void); void complex_vars_of_search (void); @@ -358,11 +400,13 @@ void complex_vars_of_syntax (void); void complex_vars_of_chartab (void); void complex_vars_of_buffer (void); +void reinit_complex_vars_of_buffer (void); void complex_vars_of_console (void); +void reinit_complex_vars_of_console (void); void complex_vars_of_emacs (void); void complex_vars_of_minibuf (void); +void reinit_complex_vars_of_minibuf (void); void complex_vars_of_callproc (void); -void complex_vars_of_filelock (void); void complex_vars_of_keymap (void); /* Reset the Lisp engine (run-time only). */ diff -r 28d9c139be4c -r 11054d720c21 src/syntax.c --- a/src/syntax.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/syntax.c Mon Aug 13 11:26:11 2007 +0200 @@ -327,6 +327,7 @@ } + #ifdef MULE /* Return 1 if there is a word boundary between two word-constituent characters C1 and C2 if they appear in this order, else return 0. @@ -337,16 +338,6 @@ && word_boundary_p (c1, c2)) extern int word_boundary_p (Emchar c1, Emchar c2); -#else -static int -word_constituent_p (struct buffer *buf, Bufpos pos, - struct Lisp_Char_Table *tab) -{ - enum syntaxcode code = SYNTAX_UNSAFE (tab, BUF_FETCH_CHAR (buf, pos)); - return ((words_include_escapes && - (code == Sescape || code == Scharquote)) - || (code == Sword)); -} #endif /* Return the position across COUNT words from FROM. @@ -358,11 +349,10 @@ { Bufpos limit = count > 0 ? BUF_ZV (buf) : BUF_BEGV (buf); struct Lisp_Char_Table *mirrortab = XCHAR_TABLE (buf->mirror_syntax_table); -#ifdef MULE Emchar ch0, ch1; enum syntaxcode code; -#endif + /* #### is it really worth it to hand expand both cases? JV */ while (count > 0) { QUIT; @@ -371,40 +361,36 @@ { if (from == limit) return 0; -#ifdef MULE + ch0 = BUF_FETCH_CHAR (buf, from); code = SYNTAX_UNSAFE (mirrortab, ch0); -#else - if (word_constituent_p (buf, from, mirrortab)) - break; -#endif - from++; -#ifdef MULE + if (words_include_escapes && (code == Sescape || code == Scharquote)) break; if (code == Sword) break; -#endif + + from++; } QUIT; - while ((from != limit) -#ifndef MULE - && word_constituent_p (buf, from, mirrortab) -#endif - ) + while (from != limit) { -#ifdef MULE ch1 = BUF_FETCH_CHAR (buf, from); code = SYNTAX_UNSAFE (mirrortab, ch1); if (!(words_include_escapes && (code == Sescape || code == Scharquote))) - if (code != Sword || WORD_BOUNDARY_P (ch0, ch1)) + if (code != Sword +#ifdef MULE + || WORD_BOUNDARY_P (ch0, ch1) +#endif + ) break; +#ifdef MULE ch0 = ch1; -#endif +#endif from++; } count--; @@ -418,12 +404,7 @@ { if (from == limit) return 0; -#ifndef MULE - if (word_constituent_p (buf, from - 1, mirrortab)) - break; -#endif - from--; -#ifdef MULE + ch1 = BUF_FETCH_CHAR (buf, from - 1); code = SYNTAX_UNSAFE (mirrortab, ch1); if (words_include_escapes @@ -431,24 +412,25 @@ break; if (code == Sword) break; -#endif + + from--; } QUIT; - while ((from != limit) -#ifndef MULE - && word_constituent_p (buf, from - 1, mirrortab) -#endif - ) + while (from != limit) { -#ifdef MULE ch0 = BUF_FETCH_CHAR (buf, from - 1); code = SYNTAX_UNSAFE (mirrortab, ch0); if (!(words_include_escapes && (code == Sescape || code == Scharquote))) - if (code != Sword || WORD_BOUNDARY_P (ch0, ch1)) + if (code != Sword +#ifdef MULE + || WORD_BOUNDARY_P (ch0, ch1) +#endif + ) break; +#ifdef MULE ch1 = ch0; #endif from--; diff -r 28d9c139be4c -r 11054d720c21 src/syntax.h --- a/src/syntax.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/syntax.h Mon Aug 13 11:26:11 2007 +0200 @@ -238,9 +238,9 @@ extern CONST unsigned char syntax_code_spec[]; -Lisp_Object scan_lists (struct buffer *buf, int from, int count, +Lisp_Object scan_lists (struct buffer *buf, Bufpos from, int count, int depth, int sexpflag, int no_error); -int char_quoted (struct buffer *buf, int pos); +int char_quoted (struct buffer *buf, Bufpos pos); /* NOTE: This does not refer to the mirror table, but to the syntax table itself. */ diff -r 28d9c139be4c -r 11054d720c21 src/syssignal.h --- a/src/syssignal.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/syssignal.h Mon Aug 13 11:26:11 2007 +0200 @@ -213,7 +213,7 @@ #define EMACS_KILLPG(gid, signo) killpg (gid, signo) #else #ifdef WINDOWSNT -#define EMACS_KILLPG(gid, signo) (kill (gid, signo)) +#define EMACS_KILLPG(gid, signo) kill (gid, signo) #else #define EMACS_KILLPG(gid, signo) kill (-(gid), signo) #endif diff -r 28d9c139be4c -r 11054d720c21 src/terminfo.c --- a/src/terminfo.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/terminfo.c Mon Aug 13 11:26:11 2007 +0200 @@ -81,7 +81,7 @@ temp = (char *) tparm (string, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9); if (outstring == 0) - outstring = ((char *) (xmalloc ((strlen (temp)) + 1))); + outstring = (char *) xmalloc (strlen (temp) + 1); strcpy (outstring, temp); return outstring; } diff -r 28d9c139be4c -r 11054d720c21 src/toolbar-msw.c --- a/src/toolbar-msw.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/toolbar-msw.c Mon Aug 13 11:26:11 2007 +0200 @@ -59,6 +59,9 @@ #define MSWINDOWS_BLANK_SIZE 5 #define MSWINDOWS_MINIMUM_TOOLBAR_SIZE 8 +static void +mswindows_move_toolbar (struct frame *f, enum toolbar_pos pos); + #define SET_TOOLBAR_WAS_VISIBLE_FLAG(frame, pos, flag) \ do { \ switch (pos) \ @@ -460,6 +463,9 @@ /* now display the window */ ShowWindow (toolbarwnd, SW_SHOW); + /* no idea why this is necessary but initial display will not + happen otherwise. */ + mswindows_move_toolbar (f, pos); if (button_tbl) xfree (button_tbl); @@ -525,6 +531,13 @@ } static void +mswindows_redraw_frame_toolbars (struct frame *f) +{ + mswindows_redraw_exposed_toolbars (f, 0, 0, FRAME_PIXWIDTH (f), + FRAME_PIXHEIGHT (f)); +} + +static void mswindows_initialize_frame_toolbars (struct frame *f) { @@ -636,5 +649,6 @@ CONSOLE_HAS_METHOD (mswindows, initialize_frame_toolbars); CONSOLE_HAS_METHOD (mswindows, free_frame_toolbars); CONSOLE_HAS_METHOD (mswindows, redraw_exposed_toolbars); + CONSOLE_HAS_METHOD (mswindows, redraw_frame_toolbars); } diff -r 28d9c139be4c -r 11054d720c21 src/toolbar-x.c --- a/src/toolbar-x.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/toolbar-x.c Mon Aug 13 11:26:11 2007 +0200 @@ -77,7 +77,8 @@ /* Draw the outline. */ x_output_shadows (f, sx, sy, swidth, sheight, top_shadow_gc, - bottom_shadow_gc, background_gc, shadow_thickness); + bottom_shadow_gc, background_gc, shadow_thickness, + EDGE_ALL); /* Blank the middle. */ XFillRectangle (dpy, x_win, background_gc, sx + shadow_thickness, @@ -158,7 +159,8 @@ x_output_shadows (f, tb->x + x_adj, tb->y + y_adj, tb->width + width_adj, tb->height + height_adj, top_shadow_gc, - bottom_shadow_gc, background_gc, shadow_thickness); + bottom_shadow_gc, background_gc, shadow_thickness, + EDGE_ALL); /* Clear the pixmap area. */ XFillRectangle (dpy, x_win, background_gc, tb->x + x_adj + shadow_thickness, @@ -211,8 +213,8 @@ } x_output_x_pixmap (f, XIMAGE_INSTANCE (instance), tb->x + x_offset, - tb->y + y_offset, 0, 0, 0, 0, width, height, - 0, 0, 0, background_gc); + tb->y + y_offset, 0, 0, width, height, + 0, 0, background_gc); } else if (IMAGE_INSTANCE_TYPE (p) == IMAGE_TEXT) { diff -r 28d9c139be4c -r 11054d720c21 src/toolbar.c --- a/src/toolbar.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/toolbar.c Mon Aug 13 11:26:11 2007 +0200 @@ -57,19 +57,19 @@ static Lisp_Object -mark_toolbar_button (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_toolbar_button (Lisp_Object obj) { struct toolbar_button *data = XTOOLBAR_BUTTON (obj); - markobj (data->next); - markobj (data->frame); - markobj (data->up_glyph); - markobj (data->down_glyph); - markobj (data->disabled_glyph); - markobj (data->cap_up_glyph); - markobj (data->cap_down_glyph); - markobj (data->cap_disabled_glyph); - markobj (data->callback); - markobj (data->enabled_p); + mark_object (data->next); + mark_object (data->frame); + mark_object (data->up_glyph); + mark_object (data->down_glyph); + mark_object (data->disabled_glyph); + mark_object (data->cap_up_glyph); + mark_object (data->cap_down_glyph); + mark_object (data->cap_disabled_glyph); + mark_object (data->callback); + mark_object (data->enabled_p); return data->help_string; } @@ -1312,6 +1312,12 @@ } void +reinit_specifier_type_create_toolbar (void) +{ + REINITIALIZE_SPECIFIER_TYPE (toolbar); +} + +void specifier_vars_of_toolbar (void) { Lisp_Object fb; diff -r 28d9c139be4c -r 11054d720c21 src/toolbar.h --- a/src/toolbar.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/toolbar.h Mon Aug 13 11:26:11 2007 +0200 @@ -73,7 +73,6 @@ #define XTOOLBAR_BUTTON(x) XRECORD (x, toolbar_button, struct toolbar_button) #define XSETTOOLBAR_BUTTON(x, p) XSETRECORD (x, p, toolbar_button) #define TOOLBAR_BUTTONP(x) RECORDP (x, toolbar_button) -#define GC_TOOLBAR_BUTTONP(x) GC_RECORDP (x, toolbar_button) #define CHECK_TOOLBAR_BUTTON(x) CHECK_RECORD (x, toolbar_button) #define CONCHECK_TOOLBAR_BUTTON(x) CONCHECK_RECORD (x, toolbar_button) diff -r 28d9c139be4c -r 11054d720c21 src/tooltalk.c --- a/src/tooltalk.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/tooltalk.c Mon Aug 13 11:26:11 2007 +0200 @@ -151,9 +151,9 @@ }; static Lisp_Object -mark_tooltalk_message (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_tooltalk_message (Lisp_Object obj) { - markobj (XTOOLTALK_MESSAGE (obj)->callback); + mark_object (XTOOLTALK_MESSAGE (obj)->callback); return XTOOLTALK_MESSAGE (obj)->plist_sym; } @@ -225,9 +225,9 @@ }; static Lisp_Object -mark_tooltalk_pattern (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_tooltalk_pattern (Lisp_Object obj) { - markobj (XTOOLTALK_PATTERN (obj)->callback); + mark_object (XTOOLTALK_PATTERN (obj)->callback); return XTOOLTALK_PATTERN (obj)->plist_sym; } diff -r 28d9c139be4c -r 11054d720c21 src/tooltalk.h --- a/src/tooltalk.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/tooltalk.h Mon Aug 13 11:26:11 2007 +0200 @@ -31,7 +31,6 @@ #define XTOOLTALK_MESSAGE(x) XRECORD (x, tooltalk_message, struct Lisp_Tooltalk_Message) #define XSETTOOLTALK_MESSAGE(x, p) XSETRECORD (x, p, tooltalk_message) #define TOOLTALK_MESSAGEP(x) RECORDP (x, tooltalk_message) -#define GC_TOOLTALK_MESSAGEP(x) GC_RECORDP (x, tooltalk_message) #define CHECK_TOOLTALK_MESSAGE(x) CHECK_RECORD (x, tooltalk_message) struct Lisp_Tooltalk_Pattern; @@ -39,7 +38,6 @@ #define XTOOLTALK_PATTERN(x) XRECORD (x, tooltalk_pattern, struct Lisp_Tooltalk_Pattern) #define XSETTOOLTALK_PATTERN(x, p) XSETRECORD (x, p, tooltalk_pattern) #define TOOLTALK_PATTERNP(x) RECORDP (x, tooltalk_pattern) -#define GC_TOOLTALK_PATTERNP(x) GC_RECORDP (x, tooltalk_pattern) #define CHECK_TOOLTALK_PATTERN(x) CHECK_RECORD (x, tooltalk_pattern) #define TOOLTALK_MESSAGE_KEY 100 diff -r 28d9c139be4c -r 11054d720c21 src/undo.c --- a/src/undo.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/undo.c Mon Aug 13 11:26:11 2007 +0200 @@ -46,7 +46,7 @@ which will be added to the list at the end of the command. This ensures we can't run out of space while trying to make an undo-boundary. */ -Lisp_Object pending_boundary; +static Lisp_Object pending_boundary; static void undo_boundary (struct buffer *b) @@ -547,9 +547,16 @@ } void +reinit_vars_of_undo (void) +{ + inside_undo = 0; +} + +void vars_of_undo (void) { - inside_undo = 0; + reinit_vars_of_undo (); + pending_boundary = Qnil; staticpro (&pending_boundary); last_undo_buffer = Qnil; diff -r 28d9c139be4c -r 11054d720c21 src/unexelf.c --- a/src/unexelf.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/unexelf.c Mon Aug 13 11:26:11 2007 +0200 @@ -18,7 +18,7 @@ the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ -/* Synched up with: FSF 20.2. */ +/* Synched up with: FSF 20.4. */ /* * unexec.c - Convert a running program into an a.out file. @@ -424,10 +424,98 @@ #include #include #include +#if !defined (__NetBSD__) && !defined (__OpenBSD__) #include +#endif #include +#if defined (__sony_news) && defined (_SYSTYPE_SYSV) +#include +#include +#endif /* __sony_news && _SYSTYPE_SYSV */ +#ifdef __sgi +#include /* for HDRR declaration */ +#endif /* __sgi */ -#if __GLIBC__ - 0 >= 2 +#if defined (__alpha__) && !defined (__NetBSD__) && !defined (__OpenBSD__) +/* Declare COFF debugging symbol table. This used to be in + /usr/include/sym.h, but this file is no longer included in Red Hat + 5.0 and presumably in any other glibc 2.x based distribution. */ +typedef struct { + short magic; + short vstamp; + int ilineMax; + int idnMax; + int ipdMax; + int isymMax; + int ioptMax; + int iauxMax; + int issMax; + int issExtMax; + int ifdMax; + int crfd; + int iextMax; + long cbLine; + long cbLineOffset; + long cbDnOffset; + long cbPdOffset; + long cbSymOffset; + long cbOptOffset; + long cbAuxOffset; + long cbSsOffset; + long cbSsExtOffset; + long cbFdOffset; + long cbRfdOffset; + long cbExtOffset; +} HDRR, *pHDRR; +#define cbHDRR sizeof(HDRR) +#define hdrNil ((pHDRR)0) +#endif + +#ifdef __NetBSD__ +/* + * NetBSD does not have normal-looking user-land ELF support. + */ +# ifdef __alpha__ +# define ELFSIZE 64 +# else +# define ELFSIZE 32 +# endif +# include + +# define PT_LOAD Elf_pt_load +# define SHT_SYMTAB Elf_sht_symtab +# define SHT_DYNSYM Elf_sht_dynsym +# define SHT_NULL Elf_sht_null +# define SHT_NOBITS Elf_sht_nobits +# define SHT_REL Elf_sht_rel +# define SHT_RELA Elf_sht_rela + +# define SHN_UNDEF Elf_eshn_undefined +# define SHN_ABS Elf_eshn_absolute +# define SHN_COMMON Elf_eshn_common + +/* + * The magic of picking the right size types is handled by the ELFSIZE + * definition above. + */ +# ifdef __STDC__ +# define ElfW(type) Elf_##type +# else +# define ElfW(type) Elf_/**/type +# endif + +# ifdef __alpha__ +# include +# define HDRR struct ecoff_symhdr +# define pHDRR HDRR * +# endif +#endif /* __NetBSD__ */ + +#ifdef __OpenBSD__ +# include +#endif + +#if __GNU_LIBRARY__ - 0 >= 6 # include /* get ElfW etc */ #endif @@ -487,8 +575,8 @@ /* Round X up to a multiple of Y. */ -static int -round_up (int x, int y) +static ElfW(Addr) +round_up (ElfW(Addr) x, ElfW(Addr) y) { int rem = x % y; if (rem == 0) @@ -531,7 +619,8 @@ ElfW(Off) new_data2_offset; ElfW(Addr) new_data2_addr; - int n, nn, old_bss_index, old_data_index; + int n, nn, old_bss_index, old_data_index, new_data2_index; + int old_sbss_index, old_mdebug_index; struct stat stat_buf; /* Open the old file & map it into the address space. */ @@ -544,7 +633,7 @@ if (fstat (old_file, &stat_buf) == -1) fatal ("Can't fstat (%s): errno %d\n", old_name, errno); - old_base = mmap (0, stat_buf.st_size, PROT_READ, MAP_SHARED, old_file, 0); + old_base = (caddr_t) mmap (0, stat_buf.st_size, PROT_READ, MAP_SHARED, old_file, 0); if (old_base == (caddr_t) -1) fatal ("Can't mmap (%s): errno %d\n", old_name, errno); @@ -580,8 +669,48 @@ if (old_bss_index == old_file_h->e_shnum) fatal ("Can't find .bss in %s.\n", old_name, 0); - old_bss_addr = OLD_SECTION_H (old_bss_index).sh_addr; - old_bss_size = OLD_SECTION_H (old_bss_index).sh_size; + for (old_sbss_index = 1; old_sbss_index < (int) old_file_h->e_shnum; + old_sbss_index++) + { +#ifdef DEBUG + fprintf (stderr, "Looking for .sbss - found %s\n", + old_section_names + OLD_SECTION_H (old_sbss_index).sh_name); +#endif + if (!strcmp (old_section_names + OLD_SECTION_H (old_sbss_index).sh_name, + ".sbss")) + break; + } + if (old_sbss_index == old_file_h->e_shnum) + { + old_sbss_index = -1; + old_bss_addr = OLD_SECTION_H(old_bss_index).sh_addr; + old_bss_size = OLD_SECTION_H(old_bss_index).sh_size; + new_data2_offset = OLD_SECTION_H(old_bss_index).sh_offset; + new_data2_index = old_bss_index; + } + else + { + old_bss_addr = OLD_SECTION_H(old_sbss_index).sh_addr; + old_bss_size = OLD_SECTION_H(old_bss_index).sh_size + + OLD_SECTION_H(old_sbss_index).sh_size; + new_data2_offset = OLD_SECTION_H(old_sbss_index).sh_offset; + new_data2_index = old_sbss_index; + } + + for (old_mdebug_index = 1; old_mdebug_index < (int) old_file_h->e_shnum; + old_mdebug_index++) + { +#ifdef DEBUG + fprintf (stderr, "Looking for .mdebug - found %s\n", + old_section_names + OLD_SECTION_H (old_mdebug_index).sh_name); +#endif + if (!strcmp (old_section_names + OLD_SECTION_H (old_mdebug_index).sh_name, + ".mdebug")) + break; + } + if (old_mdebug_index == old_file_h->e_shnum) + old_mdebug_index = 0; + #if defined (emacs) || !defined (DEBUG) new_bss_addr = (ElfW(Addr)) sbrk (0); #else @@ -589,7 +718,6 @@ #endif new_data2_addr = old_bss_addr; new_data2_size = new_bss_addr - old_bss_addr; - new_data2_offset = OLD_SECTION_H (old_bss_index).sh_offset; #ifdef DEBUG fprintf (stderr, "old_bss_index %d\n", old_bss_index); @@ -618,13 +746,13 @@ if (ftruncate (new_file, new_file_size)) fatal ("Can't ftruncate (%s): errno %d\n", new_name, errno); + new_base = (caddr_t) mmap (0, new_file_size, PROT_READ | PROT_WRITE, #ifdef UNEXEC_USE_MAP_PRIVATE - new_base = mmap (0, new_file_size, PROT_READ | PROT_WRITE, MAP_PRIVATE, - new_file, 0); + MAP_PRIVATE, #else - new_base = mmap (0, new_file_size, PROT_READ | PROT_WRITE, MAP_SHARED, - new_file, 0); + MAP_SHARED, #endif + new_file, 0); if (new_base == (caddr_t) -1) fatal ("Can't mmap (%s): errno %d\n", new_name, errno); @@ -674,24 +802,31 @@ if ((OLD_SECTION_H (old_bss_index)).sh_addralign > alignment) alignment = OLD_SECTION_H (old_bss_index).sh_addralign; -#ifndef __mips /* ifndef added by jwz at suggestion of - r02kar@x4u2.desy.de (Karsten Kuenne) to avoid - "Program segment above .bss" when dumping. - */ - if (NEW_PROGRAM_H (n).p_vaddr + NEW_PROGRAM_H (n).p_filesz > old_bss_addr) - fatal ("Program segment above .bss in %s\n", old_name, 0); -#endif /* __mips */ +#ifdef __mips + /* According to r02kar@x4u2.desy.de (Karsten Kuenne) + and oliva@gnu.org (Alexandre Oliva), on IRIX 5.2, we + always get "Program segment above .bss" when dumping + when the executable doesn't have an sbss section. */ + if (old_sbss_index != -1) +#endif /* __mips */ + if (NEW_PROGRAM_H (n).p_vaddr + NEW_PROGRAM_H (n).p_filesz + > (old_sbss_index == -1 + ? old_bss_addr + : round_up (old_bss_addr, alignment))) + fatal ("Program segment above .bss in %s\n", old_name, 0); if (NEW_PROGRAM_H (n).p_type == PT_LOAD - && (round_up ((int) ((NEW_PROGRAM_H (n)).p_vaddr - + (NEW_PROGRAM_H (n)).p_filesz), + && (round_up ((NEW_PROGRAM_H (n)).p_vaddr + + (NEW_PROGRAM_H (n)).p_filesz, alignment) - == round_up ((int) old_bss_addr, alignment))) + == round_up (old_bss_addr, alignment))) break; } if (n < 0) fatal ("Couldn't find segment next to .bss in %s\n", old_name, 0); + /* Make sure that the size includes any padding before the old .bss + section. */ NEW_PROGRAM_H (n).p_filesz = new_bss_addr - NEW_PROGRAM_H (n).p_vaddr; NEW_PROGRAM_H (n).p_memsz = NEW_PROGRAM_H (n).p_filesz; @@ -726,8 +861,10 @@ for (n = 1, nn = 1; n < (int) old_file_h->e_shnum; n++, nn++) { caddr_t src; - /* If it is bss section, insert the new data2 section before it. */ - if (n == old_bss_index) + /* If it is (s)bss section, insert the new data2 section before it. */ + /* new_data2_index is the index of either old_sbss or old_bss, that was + chosen as a section for new_data2. */ + if (n == new_data2_index) { /* Steal the data section header for this data2 section. */ memcpy (&NEW_SECTION_H (nn), &OLD_SECTION_H (old_data_index), @@ -744,21 +881,24 @@ /* Now copy over what we have in the memory now. */ memcpy (NEW_SECTION_H (nn).sh_offset + new_base, (caddr_t) OLD_SECTION_H (n).sh_addr, - /* #### mrb: should be old_bss_size instead? */ new_data2_size); nn++; } memcpy (&NEW_SECTION_H (nn), &OLD_SECTION_H (n), old_file_h->e_shentsize); - - /* The new bss section's size is zero, and its file offset and virtual - address should be off by NEW_DATA2_SIZE. */ - if (n == old_bss_index) + + if (n == old_bss_index + /* The new bss and sbss section's size is zero, and its file offset + and virtual address should be off by NEW_DATA2_SIZE. */ + || n == old_sbss_index + ) { - /* NN should be `old_bss_index + 1' at this point. */ - NEW_SECTION_H (nn).sh_offset += new_data2_size; - NEW_SECTION_H (nn).sh_addr += new_data2_size; + /* NN should be `old_s?bss_index + 1' at this point. */ + NEW_SECTION_H (nn).sh_offset = + NEW_SECTION_H (new_data2_index).sh_offset + new_data2_size; + NEW_SECTION_H (nn).sh_addr = + NEW_SECTION_H (new_data2_index).sh_addr + new_data2_size; /* Let the new bss section address alignment be the same as the section address alignment followed the old bss section, so this section will be placed in exactly the same place. */ @@ -782,7 +922,9 @@ >= OLD_SECTION_H (old_bss_index-1).sh_offset) NEW_SECTION_H (nn).sh_offset += new_data2_size; #else - if (NEW_SECTION_H (nn).sh_offset >= new_data2_offset) + if (round_up (NEW_SECTION_H (nn).sh_offset, + OLD_SECTION_H (old_bss_index).sh_addralign) + >= new_data2_offset) NEW_SECTION_H (nn).sh_offset += new_data2_size; #endif /* Any section that was originally placed after the section @@ -811,17 +953,24 @@ /* Write out the sections. .data and .data1 (and data2, called ".data" in the strings table) get copied from the current process instead of the old file. */ -#ifdef __powerpc__ - /* The PowerPC has additional 'data' segments which need to be saved */ - if (!strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".data") || - !strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".data1") || - !strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".sdata") || - !strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".sdata1")) -#else if (!strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".data") || !strcmp ((old_section_names + NEW_SECTION_H (n).sh_name), + ".sdata") + /* Taking these sections from the current process, breaks + Linux in a subtle way. Binaries only run on the + architecture (e.g. i586 vs i686) of the dumping machine */ +#ifdef __sgi + || !strcmp ((old_section_names + NEW_SECTION_H (n).sh_name), + ".lit4") + || !strcmp ((old_section_names + NEW_SECTION_H (n).sh_name), + ".lit8") + || !strcmp ((old_section_names + NEW_SECTION_H (n).sh_name), + ".got") +#endif + || !strcmp ((old_section_names + NEW_SECTION_H (n).sh_name), + ".sdata1") + || !strcmp ((old_section_names + NEW_SECTION_H (n).sh_name), ".data1")) -#endif src = (caddr_t) OLD_SECTION_H (n).sh_addr; else src = old_base + OLD_SECTION_H (n).sh_offset; @@ -829,6 +978,106 @@ memcpy (NEW_SECTION_H (nn).sh_offset + new_base, src, NEW_SECTION_H (nn).sh_size); +#ifdef __alpha__ + /* Update Alpha COFF symbol table: */ + if (strcmp (old_section_names + OLD_SECTION_H (n).sh_name, ".mdebug") + == 0) + { + pHDRR symhdr = (pHDRR) (NEW_SECTION_H (nn).sh_offset + new_base); + + symhdr->cbLineOffset += new_data2_size; + symhdr->cbDnOffset += new_data2_size; + symhdr->cbPdOffset += new_data2_size; + symhdr->cbSymOffset += new_data2_size; + symhdr->cbOptOffset += new_data2_size; + symhdr->cbAuxOffset += new_data2_size; + symhdr->cbSsOffset += new_data2_size; + symhdr->cbSsExtOffset += new_data2_size; + symhdr->cbFdOffset += new_data2_size; + symhdr->cbRfdOffset += new_data2_size; + symhdr->cbExtOffset += new_data2_size; + } +#endif /* __alpha__ */ + +#if defined (__sony_news) && defined (_SYSTYPE_SYSV) + if (NEW_SECTION_H (nn).sh_type == SHT_MIPS_DEBUG && old_mdebug_index) + { + int diff = NEW_SECTION_H(nn).sh_offset + - OLD_SECTION_H(old_mdebug_index).sh_offset; + HDRR *phdr = (HDRR *)(NEW_SECTION_H (nn).sh_offset + new_base); + + if (diff) + { + phdr->cbLineOffset += diff; + phdr->cbDnOffset += diff; + phdr->cbPdOffset += diff; + phdr->cbSymOffset += diff; + phdr->cbOptOffset += diff; + phdr->cbAuxOffset += diff; + phdr->cbSsOffset += diff; + phdr->cbSsExtOffset += diff; + phdr->cbFdOffset += diff; + phdr->cbRfdOffset += diff; + phdr->cbExtOffset += diff; + } + } +#endif /* __sony_news && _SYSTYPE_SYSV */ + +#ifdef __sgi + /* Adjust the HDRR offsets in .mdebug and copy the + line data if it's in its usual 'hole' in the object. + Makes the new file debuggable with dbx. + patches up two problems: the absolute file offsets + in the HDRR record of .mdebug (see /usr/include/syms.h), and + the ld bug that gets the line table in a hole in the + elf file rather than in the .mdebug section proper. + David Anderson. davea@sgi.com Jan 16,1994. */ + if (n == old_mdebug_index) + { +#define MDEBUGADJUST(__ct,__fileaddr) \ + if (n_phdrr->__ct > 0) \ + { \ + n_phdrr->__fileaddr += movement; \ + } + + HDRR * o_phdrr = (HDRR *)((byte *)old_base + OLD_SECTION_H (n).sh_offset); + HDRR * n_phdrr = (HDRR *)((byte *)new_base + NEW_SECTION_H (nn).sh_offset); + unsigned movement = new_data2_size; + + MDEBUGADJUST (idnMax, cbDnOffset); + MDEBUGADJUST (ipdMax, cbPdOffset); + MDEBUGADJUST (isymMax, cbSymOffset); + MDEBUGADJUST (ioptMax, cbOptOffset); + MDEBUGADJUST (iauxMax, cbAuxOffset); + MDEBUGADJUST (issMax, cbSsOffset); + MDEBUGADJUST (issExtMax, cbSsExtOffset); + MDEBUGADJUST (ifdMax, cbFdOffset); + MDEBUGADJUST (crfd, cbRfdOffset); + MDEBUGADJUST (iextMax, cbExtOffset); + /* The Line Section, being possible off in a hole of the object, + requires special handling. */ + if (n_phdrr->cbLine > 0) + { + if (o_phdrr->cbLineOffset > (OLD_SECTION_H (n).sh_offset + + OLD_SECTION_H (n).sh_size)) + { + /* line data is in a hole in elf. do special copy and adjust + for this ld mistake. + */ + n_phdrr->cbLineOffset += movement; + + memcpy (n_phdrr->cbLineOffset + new_base, + o_phdrr->cbLineOffset + old_base, n_phdrr->cbLine); + } + else + { + /* somehow line data is in .mdebug as it is supposed to be. */ + MDEBUGADJUST (cbLine, cbLineOffset); + } + } + } +#endif /* __sgi */ + /* If it is the symbol table, its st_shndx field needs to be patched. */ if (NEW_SECTION_H (nn).sh_type == SHT_SYMTAB || NEW_SECTION_H (nn).sh_type == SHT_DYNSYM) @@ -886,17 +1135,21 @@ be no harm in that provided that r_offset is always the first member. */ nn = section.sh_info; -#ifdef __powerpc__ - /* The PowerPC has additional 'data' segments which need to be saved */ - if (!strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".data") || - !strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".data1") || - !strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".sdata") || - !strcmp (old_section_names + NEW_SECTION_H (n).sh_name, ".sdata1")) -#else if (!strcmp (old_section_names + NEW_SECTION_H (nn).sh_name, ".data") || !strcmp ((old_section_names + NEW_SECTION_H (nn).sh_name), + ".sdata") +#ifdef __sgi + || !strcmp ((old_section_names + NEW_SECTION_H (nn).sh_name), + ".lit4") + || !strcmp ((old_section_names + NEW_SECTION_H (nn).sh_name), + ".lit8") + || !strcmp ((old_section_names + NEW_SECTION_H (nn).sh_name), + ".got") +#endif + || !strcmp ((old_section_names + NEW_SECTION_H (nn).sh_name), + ".sdata1") + || !strcmp ((old_section_names + NEW_SECTION_H (nn).sh_name), ".data1")) -#endif { ElfW(Addr) offset = NEW_SECTION_H (nn).sh_addr - NEW_SECTION_H (nn).sh_offset; @@ -905,6 +1158,13 @@ reloc += section.sh_entsize) { ElfW(Addr) addr = ((ElfW(Rel) *) reloc)->r_offset - offset; +#ifdef __alpha__ + /* The Alpha ELF binutils currently have a bug that + sometimes results in relocs that contain all + zeroes. Work around this for now... */ + if (((ElfW(Rel) *) reloc)->r_offset == 0) + continue; +#endif memcpy (new_base + addr, old_base + addr, sizeof(ElfW(Addr))); } } diff -r 28d9c139be4c -r 11054d720c21 src/unexnt.c --- a/src/unexnt.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/unexnt.c Mon Aug 13 11:26:11 2007 +0200 @@ -261,7 +261,7 @@ int -open_output_file (file_data *p_file, char *filename, unsigned long size) +open_output_file (file_data *p_file, CONST char *filename, unsigned long size) { HANDLE file; HANDLE file_mapping; diff -r 28d9c139be4c -r 11054d720c21 src/window.c --- a/src/window.c Mon Aug 13 11:25:03 2007 +0200 +++ b/src/window.c Mon Aug 13 11:26:11 2007 +0200 @@ -41,7 +41,7 @@ #include "gutter.h" Lisp_Object Qwindowp, Qwindow_live_p, Qwindow_configurationp; -Lisp_Object Qscroll_up, Qscroll_down, Qdisplay_buffer; +Lisp_Object Qdisplay_buffer; #ifdef MEMORY_USAGE_STATS Lisp_Object Qface_cache, Qglyph_cache, Qline_start_cache, Qother_redisplay; @@ -85,6 +85,9 @@ /* Spacing between outer egde of divider border and window edge */ Lisp_Object Vvertical_divider_spacing; +/* How much to scroll by per-line. */ +Lisp_Object Vwindow_pixel_scroll_increment; + /* Scroll if point lands on the bottom line and that line is partially clipped. */ int scroll_on_clipped_lines; @@ -118,7 +121,7 @@ int next_screen_context_lines; /* List of freed window configurations with 1 - 10 windows. */ -Lisp_Object Vwindow_configuration_free_list[10]; +static Lisp_Object Vwindow_configuration_free_list[10]; #define SET_LAST_MODIFIED(w, cache_too) \ do { \ @@ -138,38 +141,38 @@ #define MARK_DISP_VARIABLE(field) \ - markobj (window->field[CURRENT_DISP]); \ - markobj (window->field[DESIRED_DISP]); \ - markobj (window->field[CMOTION_DISP]); + mark_object (window->field[CURRENT_DISP]); \ + mark_object (window->field[DESIRED_DISP]); \ + mark_object (window->field[CMOTION_DISP]); static Lisp_Object -mark_window (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_window (Lisp_Object obj) { struct window *window = XWINDOW (obj); - markobj (window->frame); - markobj (window->mini_p); - markobj (window->next); - markobj (window->prev); - markobj (window->hchild); - markobj (window->vchild); - markobj (window->parent); - markobj (window->buffer); + mark_object (window->frame); + mark_object (window->mini_p); + mark_object (window->next); + mark_object (window->prev); + mark_object (window->hchild); + mark_object (window->vchild); + mark_object (window->parent); + mark_object (window->buffer); MARK_DISP_VARIABLE (start); MARK_DISP_VARIABLE (pointm); - markobj (window->sb_point); /* #### move to scrollbar.c? */ - markobj (window->use_time); + mark_object (window->sb_point); /* #### move to scrollbar.c? */ + mark_object (window->use_time); MARK_DISP_VARIABLE (last_modified); MARK_DISP_VARIABLE (last_point); MARK_DISP_VARIABLE (last_start); MARK_DISP_VARIABLE (last_facechange); - markobj (window->line_cache_last_updated); - markobj (window->redisplay_end_trigger); - markobj (window->subwindow_instance_cache); - - mark_face_cachels (window->face_cachels, markobj); - mark_glyph_cachels (window->glyph_cachels, markobj); - -#define WINDOW_SLOT(slot, compare) ((void) (markobj (window->slot))) + mark_object (window->line_cache_last_updated); + mark_object (window->redisplay_end_trigger); + mark_object (window->subwindow_instance_cache); + + mark_face_cachels (window->face_cachels); + mark_glyph_cachels (window->glyph_cachels); + +#define WINDOW_SLOT(slot, compare) mark_object (window->slot) #include "winslots.h" return Qnil; @@ -706,6 +709,11 @@ int window_truncation_on (struct window *w) { + /* Minibuffer windows are never truncated. + ### is this the right way ? */ + if (MINI_WINDOW_P (w)) + return 0; + /* Horizontally scrolled windows are truncated. */ if (w->hscroll) return 1; @@ -724,6 +732,17 @@ return 0; } +DEFUN ("window-truncated-p", Fwindow_truncated_p, 0, 1, 0, /* +Returns Non-Nil iff the window is truncated. +*/ + (window)) +{ + struct window *w = decode_window (window); + + return window_truncation_on (w) ? Qt : Qnil; +} + + static int have_undivided_common_edge (struct window *w_right, void *closure) { @@ -1096,6 +1115,26 @@ } } +DEFUN ("last-nonminibuf-window", Flast_nonminibuf_window, 0, 1, 0, /* +Return the last selected window that is not a minibuffer window. +If the optional argument CON-DEV-OR-FRAME is specified and is a frame, +return the last non-minibuffer window used by that frame. If +CON-DEV-OR-FRAME is a device, then the selected frame on that device +will be used. If CON-DEV-OR-FRAME is a console, the selected frame on +that console's selected device will be used. Otherwise, the selected +frame is used. +*/ + (con_dev_or_frame)) +{ + if (NILP (con_dev_or_frame) && NILP (Fselected_device (Qnil))) + return Qnil; /* happens at startup */ + + { + struct frame *f = decode_frame_or_selected (con_dev_or_frame); + return FRAME_LAST_NONMINIBUF_WINDOW (f); + } +} + DEFUN ("minibuffer-window", Fminibuffer_window, 0, 1, 0, /* Return the window used now for minibuffers. If the optional argument CON-DEV-OR-FRAME is specified and is a frame, return @@ -3910,7 +3949,8 @@ -/* Scroll contents of window WINDOW up N lines. */ +/* Scroll contents of window WINDOW up N lines. If N < (top line height / + average line height) then we just adjust the top clip. */ void window_scroll (Lisp_Object window, Lisp_Object n, int direction, Error_behavior errb) @@ -3920,6 +3960,9 @@ int selected = EQ (window, Fselected_window (Qnil)); int value = 0; Lisp_Object point, tem; + display_line_dynarr *dla; + int fheight, fwidth, modeline = 0; + struct display_line* dl; if (selected) point = make_int (BUF_PT (b)); @@ -3949,6 +3992,7 @@ window, Qnil); Fset_marker (w->start[CURRENT_DISP], point, w->buffer); w->start_at_line_beg = beginning_of_line_p (b, XINT (point)); + WINDOW_TEXT_TOP_CLIP (w) = 0; MARK_WINDOWS_CHANGED (w); } @@ -3992,82 +4036,146 @@ { return; } - else if (value > 0) + + /* Determine parameters to test for partial line scrolling with. */ + dla = window_display_lines (w, CURRENT_DISP); + + if (INTP (Vwindow_pixel_scroll_increment)) + fheight = XINT (Vwindow_pixel_scroll_increment); + else if (!NILP (Vwindow_pixel_scroll_increment)); + default_face_height_and_width (window, &fheight, &fwidth); + + if (Dynarr_length (dla) >= 1) + modeline = Dynarr_atp (dla, 0)->modeline; + + dl = Dynarr_atp (dla, modeline); + + if (value > 0) { - int vtarget; - Bufpos startp, old_start; - - old_start = marker_position (w->start[CURRENT_DISP]); - startp = vmotion (w, old_start, value, &vtarget); - - if (vtarget < value && - (w->window_end_pos[CURRENT_DISP] == -1 - || (BUF_Z (b) - w->window_end_pos[CURRENT_DISP] > BUF_ZV (b)))) + /* Go for partial display line scrolling. This just means bumping + the clip by a reasonable amount and redisplaying, everything else + remains unchanged. */ + if (!NILP (Vwindow_pixel_scroll_increment) + && + Dynarr_length (dla) >= (1 + modeline) + && + (dl->ascent - dl->top_clip) - fheight * value > 0) { - maybe_signal_error (Qend_of_buffer, Qnil, Qwindow, errb); - return; + WINDOW_TEXT_TOP_CLIP (w) += value * fheight; + MARK_WINDOWS_CHANGED (w); } else { - set_marker_restricted (w->start[CURRENT_DISP], make_int (startp), - w->buffer); - w->force_start = 1; - w->start_at_line_beg = beginning_of_line_p (b, startp); - MARK_WINDOWS_CHANGED (w); - - if (!point_would_be_visible (w, startp, XINT (point))) + int vtarget; + Bufpos startp, old_start; + + if (WINDOW_TEXT_TOP_CLIP (w)) + { + WINDOW_TEXT_TOP_CLIP (w) = 0; + MARK_WINDOWS_CHANGED (w); + } + + old_start = marker_position (w->start[CURRENT_DISP]); + startp = vmotion (w, old_start, value, &vtarget); + + if (vtarget < value && + (w->window_end_pos[CURRENT_DISP] == -1 + || (BUF_Z (b) - w->window_end_pos[CURRENT_DISP] > BUF_ZV (b)))) { - if (selected) - BUF_SET_PT (b, startp); - else - set_marker_restricted (w->pointm[CURRENT_DISP], - make_int (startp), - w->buffer); + maybe_signal_error (Qend_of_buffer, Qnil, Qwindow, errb); + return; + } + else + { + set_marker_restricted (w->start[CURRENT_DISP], make_int (startp), + w->buffer); + w->force_start = 1; + w->start_at_line_beg = beginning_of_line_p (b, startp); + MARK_WINDOWS_CHANGED (w); + + if (!point_would_be_visible (w, startp, XINT (point))) + { + if (selected) + BUF_SET_PT (b, startp); + else + set_marker_restricted (w->pointm[CURRENT_DISP], + make_int (startp), + w->buffer); + } } } } else if (value < 0) { - int vtarget; - Bufpos startp, old_start; - - old_start = marker_position (w->start[CURRENT_DISP]); - startp = vmotion (w, old_start, value, &vtarget); - - if (vtarget > value - && marker_position (w->start[CURRENT_DISP]) == BUF_BEGV (b)) + /* Go for partial display line scrolling. This just means bumping + the clip by a reasonable amount and redisplaying, everything else + remains unchanged. */ + if (!NILP (Vwindow_pixel_scroll_increment) + && + Dynarr_length (dla) >= (1 + modeline) + && + (dl->ascent - dl->top_clip) - fheight * value < + (dl->ascent + dl->descent - dl->clip) + && + WINDOW_TEXT_TOP_CLIP (w) + value * fheight > 0) { - maybe_signal_error (Qbeginning_of_buffer, Qnil, Qwindow, errb); - return; + WINDOW_TEXT_TOP_CLIP (w) += value * fheight; + MARK_WINDOWS_CHANGED (w); } else { - set_marker_restricted (w->start[CURRENT_DISP], make_int (startp), - w->buffer); - w->force_start = 1; - w->start_at_line_beg = beginning_of_line_p (b, startp); - MARK_WINDOWS_CHANGED (w); - - if (!point_would_be_visible (w, startp, XINT (point))) + int vtarget; + Bufpos startp, old_start; + + if (WINDOW_TEXT_TOP_CLIP (w)) + { + WINDOW_TEXT_TOP_CLIP (w) = 0; + MARK_WINDOWS_CHANGED (w); + } + + old_start = marker_position (w->start[CURRENT_DISP]); + startp = vmotion (w, old_start, value, &vtarget); + + if (vtarget > value + && marker_position (w->start[CURRENT_DISP]) == BUF_BEGV (b)) + { + maybe_signal_error (Qbeginning_of_buffer, Qnil, Qwindow, errb); + return; + } + else { - Bufpos new_point; - - if (MINI_WINDOW_P (w)) - new_point = startp; - else - new_point = start_of_last_line (w, startp); - - if (selected) - BUF_SET_PT (b, new_point); - else - set_marker_restricted (w->pointm[CURRENT_DISP], - make_int (new_point), - w->buffer); + set_marker_restricted (w->start[CURRENT_DISP], make_int (startp), + w->buffer); + w->force_start = 1; + w->start_at_line_beg = beginning_of_line_p (b, startp); + MARK_WINDOWS_CHANGED (w); + + if (!point_would_be_visible (w, startp, XINT (point))) + { + Bufpos new_point; + + if (MINI_WINDOW_P (w)) + new_point = startp; + else + new_point = start_of_last_line (w, startp); + + if (selected) + BUF_SET_PT (b, new_point); + else + set_marker_restricted (w->pointm[CURRENT_DISP], + make_int (new_point), + w->buffer); + } } } } else /* value == 0 && direction == -1 */ { + if (WINDOW_TEXT_TOP_CLIP (w)) + { + WINDOW_TEXT_TOP_CLIP (w) = 0; + MARK_WINDOWS_CHANGED (w); + } if (marker_position (w->start[CURRENT_DISP]) == BUF_BEGV (b)) { maybe_signal_error (Qbeginning_of_buffer, Qnil, Qwindow, errb); @@ -4105,7 +4213,6 @@ } } } - } DEFUN ("scroll-up", Fscroll_up, 0, 1, "_P", /* @@ -4622,32 +4729,32 @@ #define CHECK_WINDOW_CONFIGURATION(x) CHECK_RECORD (x, window_configuration) static Lisp_Object -mark_window_config (Lisp_Object obj, void (*markobj) (Lisp_Object)) +mark_window_config (Lisp_Object obj) { struct window_config *config = XWINDOW_CONFIGURATION (obj); int i; - markobj (config->current_window); - markobj (config->current_buffer); - markobj (config->minibuffer_scroll_window); - markobj (config->root_window); + mark_object (config->current_window); + mark_object (config->current_buffer); + mark_object (config->minibuffer_scroll_window); + mark_object (config->root_window); for (i = 0; i < config->saved_windows_count; i++) { struct saved_window *s = SAVED_WINDOW_N (config, i); - markobj (s->window); - markobj (s->buffer); - markobj (s->start); - markobj (s->pointm); - markobj (s->sb_point); - markobj (s->mark); + mark_object (s->window); + mark_object (s->buffer); + mark_object (s->start); + mark_object (s->pointm); + mark_object (s->sb_point); + mark_object (s->mark); #if 0 /* #### This looked like this. I do not see why specifier cached values should not be marked, as such specifiers as toolbars might have GC-able instances. Freed configs are not marked, aren't they? -- kkm */ - markobj (s->dedicated); + mark_object (s->dedicated); #else -#define WINDOW_SLOT(slot, compare) ((void) (markobj (s->slot))) +#define WINDOW_SLOT(slot, compare) mark_object (s->slot) #include "winslots.h" #endif } @@ -5050,7 +5157,7 @@ SET_LAST_FACECHANGE (w); w->config_mark = 0; -#define WINDOW_SLOT(slot, compare) w->slot = p->slot; +#define WINDOW_SLOT(slot, compare) w->slot = p->slot #include "winslots.h" /* Reinstall the saved buffer and pointers into it. */ @@ -5324,7 +5431,7 @@ p->hscroll = w->hscroll; p->modeline_hscroll = w->modeline_hscroll; -#define WINDOW_SLOT(slot, compare) p->slot = w->slot; +#define WINDOW_SLOT(slot, compare) p->slot = w->slot #include "winslots.h" if (!NILP (w->buffer)) @@ -5466,6 +5573,78 @@ return unbind_to (speccount, val); } +DEFUN ("current-pixel-column", Fcurrent_pixel_column, 0, 2, 0, /* +Return the horizontal pixel position of POS in window. +Beginning of line is column 0. This is calculated using the redisplay +display tables. If WINDOW is nil, the current window is assumed. +If POS is nil, point is assumed. Note that POS must be visible for +a non-nil result to be returned. +*/ + (window, pos)) +{ + struct window* w = decode_window (window); + display_line_dynarr *dla = window_display_lines (w, CURRENT_DISP); + + struct display_line *dl = 0; + struct display_block *db = 0; + struct rune* rb = 0; + int y = w->last_point_y[CURRENT_DISP]; + int x = w->last_point_x[CURRENT_DISP]; + + if (MINI_WINDOW_P (w)) + return Qnil; + + if (y<0 || x<0 || y >= Dynarr_length (dla) || !NILP (pos)) + { + int first_line, i; + Bufpos point; + + if (NILP (pos)) + pos = Fwindow_point (window); + + CHECK_INT (pos); + point = XINT (pos); + + if (Dynarr_length (dla) && Dynarr_atp (dla, 0)->modeline) + first_line = 1; + else + first_line = 0; + + for (i = first_line; i < Dynarr_length (dla); i++) + { + dl = Dynarr_atp (dla, i); + /* find the vertical location first */ + if (point >= dl->bufpos && point <= dl->end_bufpos) + { + db = get_display_block_from_line (dl, TEXT); + for (i = 0; i < Dynarr_length (db->runes); i++) + { + rb = Dynarr_atp (db->runes, i); + if (point <= rb->bufpos) + goto found_bufpos; + } + return Qnil; + } + } + return Qnil; + found_bufpos: + ; + } + else + { + /* optimised case */ + dl = Dynarr_atp (dla, y); + db = get_display_block_from_line (dl, TEXT); + + if (x >= Dynarr_length (db->runes)) + return Qnil; + + rb = Dynarr_atp (db->runes, x); + } + + return make_int (rb->xpos - WINDOW_LEFT (w)); +} + #ifdef DEBUG_XEMACS /* This is short and simple in elisp, but... it was written to debug @@ -5518,8 +5697,6 @@ defsymbol (&Qwindowp, "windowp"); defsymbol (&Qwindow_live_p, "window-live-p"); defsymbol (&Qwindow_configurationp, "window-configuration-p"); - defsymbol (&Qscroll_up, "scroll-up"); - defsymbol (&Qscroll_down, "scroll-down"); defsymbol (&Qtemp_buffer_show_hook, "temp-buffer-show-hook"); defsymbol (&Qdisplay_buffer, "display-buffer"); @@ -5535,6 +5712,7 @@ #endif DEFSUBR (Fselected_window); + DEFSUBR (Flast_nonminibuf_window); DEFSUBR (Fminibuffer_window); DEFSUBR (Fwindow_minibuffer_p); DEFSUBR (Fwindowp); @@ -5545,6 +5723,7 @@ DEFSUBR (Fwindow_previous_child); DEFSUBR (Fwindow_parent); DEFSUBR (Fwindow_lowest_p); + DEFSUBR (Fwindow_truncated_p); DEFSUBR (Fwindow_highest_p); DEFSUBR (Fwindow_leftmost_p); DEFSUBR (Fwindow_rightmost_p); @@ -5613,14 +5792,30 @@ DEFSUBR (Fset_window_configuration); DEFSUBR (Fcurrent_window_configuration); DEFSUBR (Fsave_window_excursion); + DEFSUBR (Fcurrent_pixel_column); +} + +void +reinit_vars_of_window (void) +{ + int i; + /* Make sure all windows get marked */ + minibuf_window = Qnil; + staticpro_nodump (&minibuf_window); + + for (i = 0; i < countof (Vwindow_configuration_free_list); i++) + { + Vwindow_configuration_free_list[i] = + make_lcrecord_list (sizeof_window_config_for_n_windows (i + 1), + &lrecord_window_configuration); + staticpro_nodump (&Vwindow_configuration_free_list[i]); + } } void vars_of_window (void) { - /* Make sure all windows get marked */ - minibuf_window = Qnil; - staticpro (&minibuf_window); + reinit_vars_of_window (); DEFVAR_BOOL ("scroll-on-clipped-lines", &scroll_on_clipped_lines /* *Non-nil means to scroll if point lands on a line which is clipped. @@ -5651,6 +5846,13 @@ */ ); Vother_window_scroll_buffer = Qnil; + DEFVAR_LISP ("window-pixel-scroll-increment", &Vwindow_pixel_scroll_increment /* +*Number of pixels to scroll by per requested line. +If nil then normal line scrolling occurs regardless of line height. +If t then scrolling is done in increments equal to the height of the default face. +*/ ); + Vwindow_pixel_scroll_increment = Qt; + DEFVAR_INT ("next-screen-context-lines", &next_screen_context_lines /* *Number of lines of continuity when scrolling by screenfuls. */ ); @@ -5665,18 +5867,6 @@ *Delete any window less than this wide. */ ); window_min_width = 10; - - { - int i; - - for (i = 0; i < countof (Vwindow_configuration_free_list); i++) - { - Vwindow_configuration_free_list[i] = - make_lcrecord_list (sizeof_window_config_for_n_windows (i + 1), - &lrecord_window_configuration); - staticpro (&Vwindow_configuration_free_list[i]); - } - } } void diff -r 28d9c139be4c -r 11054d720c21 src/window.h --- a/src/window.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/window.h Mon Aug 13 11:26:11 2007 +0200 @@ -130,6 +130,14 @@ int hscroll; /* Idem for the window's modeline */ int modeline_hscroll; + /* Amount to clip off the top line for pixel-based scrolling. Point + will remain constant but this will be incremented to + incrementally shift lines up. */ + int top_yoffset; + /* Amount to clip off the left of the lines for pixel-based + scrolling. Hscroll will remain constant but this will be + incremented to incrementally shift lines left.*/ + int left_xoffset; /* Number saying how recently window was selected */ Lisp_Object use_time; /* text.modified of displayed buffer as of last time display completed */ @@ -254,7 +262,6 @@ #define XWINDOW(x) XRECORD (x, window, struct window) #define XSETWINDOW(x, p) XSETRECORD (x, p, window) #define WINDOWP(x) RECORDP (x, window) -#define GC_WINDOWP(x) GC_RECORDP (x, window) #define CHECK_WINDOW(x) CHECK_RECORD (x, window) #define CONCHECK_WINDOW(x) CONCHECK_RECORD (x, window) @@ -382,6 +389,7 @@ /* XEmacs window size and positioning macros. */ #define WINDOW_TOP(w) ((w)->pixel_top) #define WINDOW_TEXT_TOP(w) (WINDOW_TOP (w) + window_top_gutter_height (w)) +#define WINDOW_TEXT_TOP_CLIP(w) ((w)->top_yoffset) #define WINDOW_BOTTOM(w) ((w)->pixel_top + (w)->pixel_height) #define WINDOW_TEXT_BOTTOM(w) (WINDOW_BOTTOM (w) - window_bottom_gutter_height (w)) #define WINDOW_LEFT(w) ((w)->pixel_left) diff -r 28d9c139be4c -r 11054d720c21 src/xmu.h --- a/src/xmu.h Mon Aug 13 11:25:03 2007 +0200 +++ b/src/xmu.h Mon Aug 13 11:26:11 2007 +0200 @@ -9,6 +9,7 @@ # include # include # include +# include /* Do the EDITRES protocol if running X11R5 (or later) version */ #if (XtSpecificationRelease >= 5) @@ -27,5 +28,11 @@ int XmuPrintDefaultErrorMessage (Display *dpy, XErrorEvent *event, FILE *fp); void XmuCopyISOLatin1Lowered (char *, CONST char *); +#define Max(x, y) (((x) > (y)) ? (x) : (y)) +#define Min(x, y) (((x) < (y)) ? (x) : (y)) +#define AssignMax(x, y) {if ((y) > (x)) x = (y);} +#define AssignMin(x, y) {if ((y) < (x)) x = (y);} +typedef enum {XtorientHorizontal, XtorientVertical} XtOrientation; + #endif diff -r 28d9c139be4c -r 11054d720c21 tests/ChangeLog --- a/tests/ChangeLog Mon Aug 13 11:25:03 2007 +0200 +++ b/tests/ChangeLog Mon Aug 13 11:26:11 2007 +0200 @@ -1,3 +1,7 @@ +1999-11-10 XEmacs Build Bot + + * XEmacs 21.2.20 is released + 1999-07-30 XEmacs Build Bot * XEmacs 21.2.19 is released diff -r 28d9c139be4c -r 11054d720c21 tests/automated/hash-table-tests.el --- a/tests/automated/hash-table-tests.el Mon Aug 13 11:25:03 2007 +0200 +++ b/tests/automated/hash-table-tests.el Mon Aug 13 11:26:11 2007 +0200 @@ -37,30 +37,41 @@ (require 'test-harness)))) ;; Test all combinations of make-hash-table keywords -(dolist (type '(non-weak weak key-weak value-weak)) - (dolist (test '(eq eql equal)) - (dolist (size '(0 1 100)) - (dolist (rehash-size '(1.1 9.9)) - (dolist (rehash-threshold '(0.2 .9)) +(dolist (test '(eq eql equal)) + (dolist (size '(0 1 100)) + (dolist (rehash-size '(1.1 9.9)) + (dolist (rehash-threshold '(0.2 .9)) + (dolist (weakness '(nil t key value)) (dolist (data '(() (1 2) (1 2 3 4))) - (let ((ht (make-hash-table :test test - :type type - :size size - :rehash-size rehash-size - :rehash-threshold rehash-threshold))) + (let ((ht (make-hash-table + :test test + :size size + :rehash-size rehash-size + :rehash-threshold rehash-threshold + :weakness weakness))) (Assert (equal ht (car (let ((print-readably t)) (read-from-string (prin1-to-string ht)))))) (Assert (eq test (hash-table-test ht))) - (Assert (eq type (hash-table-type ht))) (Assert (<= size (hash-table-size ht))) (Assert (eql rehash-size (hash-table-rehash-size ht))) - (Assert (eql rehash-threshold (hash-table-rehash-threshold ht)))))))))) + (Assert (eql rehash-threshold (hash-table-rehash-threshold ht))) + (Assert (eq weakness (hash-table-weakness ht)))))))))) + +(loop for (fun weakness) in '((make-hashtable nil) + (make-weak-hashtable t) + (make-key-weak-hashtable key) + (make-value-weak-hashtable value)) + do (Assert (eq weakness (hash-table-weakness (funcall fun 10))))) -(loop for (fun type) in '((make-hashtable non-weak) - (make-weak-hashtable weak) - (make-key-weak-hashtable key-weak) - (make-value-weak-hashtable value-weak)) - do (Assert (eq type (hash-table-type (funcall fun 10))))) +(loop for (type weakness) in '((non-weak nil) + (weak t) + (key-weak key) + (value-weak value)) + do (Assert (equal (make-hash-table :type type) + (make-hash-table :weakness weakness)))) + +(Assert (not (equal (make-hash-table :weakness nil) + (make-hash-table :weakness t)))) (let ((ht (make-hash-table :size 20 :rehash-threshold .75 :test 'eq)) (size 80)) @@ -69,6 +80,7 @@ (Assert (eq 'eq (hash-table-test ht))) (Assert (eq 'non-weak (hash-table-type ht))) (Assert (eq 'non-weak (hashtable-type ht))) + (Assert (eq 'nil (hash-table-weakness ht))) (dotimes (j size) (puthash j (- j) ht) (Assert (eq (gethash j ht) (- j))) @@ -193,13 +205,13 @@ )) ;; Test that weak hash-tables are properly handled -(loop for (type expected-count expected-k-sum expected-v-sum) in - '((non-weak 6 38 25) - (weak 3 6 9) - (key-weak 4 38 9) - (value-weak 4 6 25)) +(loop for (weakness expected-count expected-k-sum expected-v-sum) in + '((nil 6 38 25) + (t 3 6 9) + (key 4 38 9) + (value 4 6 25)) do - (let* ((ht (make-hash-table :type type)) + (let* ((ht (make-hash-table :weakness weakness)) (my-obj (cons ht ht))) (garbage-collect) (puthash my-obj 1 ht) @@ -238,9 +250,9 @@ (Assert (= v-sum k-sum)))) ;;; Test reading and printing of hash-table objects -(let ((h1 #s(hashtable type weak rehash-size 3.0 rehash-threshold .2 test eq data (1 2 3 4))) - (h2 #s(hash-table type weak rehash-size 3.0 rehash-threshold .2 test eq data (1 2 3 4))) - (h3 (make-hash-table :type 'weak :rehash-size 3.0 :rehash-threshold .2 :test 'eq))) +(let ((h1 #s(hashtable weakness t rehash-size 3.0 rehash-threshold .2 test eq data (1 2 3 4))) + (h2 #s(hash-table weakness t rehash-size 3.0 rehash-threshold .2 test eq data (1 2 3 4))) + (h3 (make-hash-table :weakness t :rehash-size 3.0 :rehash-threshold .2 :test 'eq))) (Assert (equal h1 h2)) (Assert (not (equal h1 h3))) (puthash 1 2 h3) @@ -267,3 +279,7 @@ (clrhash h2) (Assert (equal h1 h2)) ) + +;;; Test sxhash +(Assert (= (sxhash "foo") (sxhash "foo"))) +(Assert (= (sxhash '(1 2 3)) (sxhash '(1 2 3)))) diff -r 28d9c139be4c -r 11054d720c21 tests/automated/lisp-tests.el --- a/tests/automated/lisp-tests.el Mon Aug 13 11:25:03 2007 +0200 +++ b/tests/automated/lisp-tests.el Mon Aug 13 11:26:11 2007 +0200 @@ -229,6 +229,8 @@ (Assert (= (+ 1.0 1) 2.0)) (Assert (= (+ 1.0 1 1) 3.0)) (Assert (= (+ 1 1 1.0) 3.0)) +(Assert (eq (1+ most-positive-fixnum) most-negative-fixnum)) +(Assert (eq (+ most-positive-fixnum 1) most-negative-fixnum)) ;; Test `-' (Check-Error wrong-number-of-arguments (-)) @@ -253,6 +255,9 @@ (Assert (= (- 1.5 1) .5)) (Assert (= (- 1 1.5) (- .5))) +(Assert (eq (1- most-negative-fixnum) most-positive-fixnum)) +(Assert (eq (- most-negative-fixnum 1) most-positive-fixnum)) + ;; Test `/' ;; Test division by zero errors diff -r 28d9c139be4c -r 11054d720c21 tests/glyph-test.el --- a/tests/glyph-test.el Mon Aug 13 11:25:03 2007 +0200 +++ b/tests/glyph-test.el Mon Aug 13 11:26:11 2007 +0200 @@ -1,24 +1,28 @@ -(setq str "Hello There") (set-extent-begin-glyph - (make-extent 0 0 str) - (make-glyph [xpm :file "../etc/xemacs-icon.xpm"])) + (make-extent (point) (point)) + (setq im (make-glyph [xpm :file "xemacs-icon.xpm"]))) (defun foo () - (interactive) - (ding)) -; (setq ok-select (not ok-select))) + (interactive) + (setq ok-select (not ok-select))) + +(defun fee () (interactive) (message "hello")) ;; button in a group (setq ok-select nil) (set-extent-begin-glyph (make-extent (point) (point)) - (make-glyph [button :descriptor ["ok " (setq ok-select t) - :style radio :selected ok-select]])) + (setq radio-button1 + (make-glyph + [button :descriptor ["ok " (setq ok-select t) + :style radio :selected ok-select]]))) ;; button in a group (set-extent-begin-glyph (make-extent (point) (point)) - (make-glyph [button :descriptor ["ok" (setq ok-select nil) :style radio - :selected (not ok-select)]])) + (setq radio-button2 + (make-glyph + [button :descriptor ["ok" (setq ok-select nil) :style radio + :selected (not ok-select)]]))) ;; toggle button (set-extent-begin-glyph (make-extent (point) (point)) @@ -28,19 +32,20 @@ :selected (not ok-select)]]))) (set-extent-begin-glyph (make-extent (point) (point)) - (make-glyph [button :descriptor ["ok" :style toggle - :callback - (setq ok-select (not ok-select)) - :selected ok-select]])) + (setq toggle-button + (make-glyph [button :descriptor ["ok" :style toggle + :callback + (setq ok-select (not ok-select)) + :selected ok-select]]))) ;; normal pushbutton (set-extent-begin-glyph (make-extent (point) (point)) - (setq pbutton (make-glyph - [button :width 10 :height 2 - :face modeline-mousable - :descriptor "ok" :callback foo - :selected t]))) + (setq push-button + (make-glyph [button :width 10 :height 2 + :face modeline-mousable + :descriptor "ok" :callback foo + :selected t]))) ;; tree view (set-extent-begin-glyph (make-extent (point) (point)) @@ -58,9 +63,9 @@ (make-extent (point) (point)) (setq tab (make-glyph [tab-control :descriptor "My Tab" - :face default + :face highlight :properties (:items (["One" foo] - ["Two" foo] + ["Two" fee] ["Three" foo]))]))) ;; progress gauge @@ -94,8 +99,7 @@ (make-glyph [button :face modeline-mousable :descriptor "ok" :callback foo - :image (make-glyph - [xpm :file "../etc/xemacs-icon.xpm"])])) + :image [xpm :file "../etc/xemacs-icon.xpm"]])) ;; normal pushbutton (set-extent-begin-glyph @@ -105,20 +109,25 @@ ;; edit box (set-extent-begin-glyph (make-extent (point) (point)) - (setq hedit (make-glyph [edit-field :pixel-width 50 :pixel-height 30 - :face bold-italic - :descriptor ["Hello"]]))) + (setq edit-field (make-glyph [edit-field :pixel-width 50 :pixel-height 30 + :face bold-italic + :descriptor ["Hello"]]))) ;; combo box (set-extent-begin-glyph (make-extent (point) (point)) - (setq hcombo (make-glyph - [combo-box :width 10 :height 3 :descriptor ["Hello"] - :properties (:items ("One" "Two" "Three"))]))) + (setq combo-box (make-glyph + [combo-box :width 10 :descriptor ["Hello"] + :properties (:items ("One" "Two" "Three"))]))) -;; line +;; label (set-extent-begin-glyph (make-extent (point) (point)) - (make-glyph [label :pixel-width 150 :descriptor "Hello"])) + (setq label (make-glyph [label :pixel-width 150 :descriptor "Hello"]))) + +;; string +(set-extent-begin-glyph + (make-extent (point) (point)) + (setq str (make-glyph [string :data "Hello There"]))) ;; scrollbar ;(set-extent-begin-glyph @@ -129,3 +138,17 @@ (setq sw (make-glyph [subwindow :pixel-width 50 :pixel-height 70])) (set-extent-begin-glyph (make-extent (point) (point)) sw) +;; layout +(setq layout + (make-glyph + [layout :pixel-width 200 :pixel-height 250 + :orientation vertical + :justify left + :border [string :data "Hello There Mrs"] + :items ([layout :orientation horizontal + :items (radio-button1 radio-button2)] + edit-field toggle-button label str)])) +(set-glyph-face layout 'gui-element) +(set-extent-begin-glyph + (make-extent (point) (point)) layout) + diff -r 28d9c139be4c -r 11054d720c21 version.sh --- a/version.sh Mon Aug 13 11:25:03 2007 +0200 +++ b/version.sh Mon Aug 13 11:26:11 2007 +0200 @@ -2,8 +2,8 @@ emacs_is_beta=t emacs_major_version=21 emacs_minor_version=2 -emacs_beta_version=19 -xemacs_codename="Shinjuku" +emacs_beta_version=20 +xemacs_codename="Yoko" infodock_major_version=4 infodock_minor_version=0 infodock_build_version=8