diff options
| author | Eli Zaretskii | 2001-01-27 19:18:02 +0000 |
|---|---|---|
| committer | Eli Zaretskii | 2001-01-27 19:18:02 +0000 |
| commit | 437368feddb7d80bd2e5e2c3d0d982ecc765ef3c (patch) | |
| tree | b9cedfa2b198a4f59c1ec4b73b0dc043bb9b969a | |
| parent | e26f9ced787fe5522a8d2c3b8d4bab9f29d0cf55 (diff) | |
| download | emacs-437368feddb7d80bd2e5e2c3d0d982ecc765ef3c.tar.gz emacs-437368feddb7d80bd2e5e2c3d0d982ecc765ef3c.zip | |
Expand and update, based on the instructions to
pretesters, nt/INSTALL, and private communications and experience.
| -rw-r--r-- | etc/ChangeLog | 5 | ||||
| -rw-r--r-- | etc/DEBUG | 365 |
2 files changed, 364 insertions, 6 deletions
diff --git a/etc/ChangeLog b/etc/ChangeLog index 08503a537d4..a3a12a3716e 100644 --- a/etc/ChangeLog +++ b/etc/ChangeLog | |||
| @@ -1,3 +1,8 @@ | |||
| 1 | 2001-01-27 Eli Zaretskii <eliz@is.elta.co.il> | ||
| 2 | |||
| 3 | * DEBUG: Expand and update, based on the instructions to | ||
| 4 | pretesters, nt/INSTALL, and private communications and experience. | ||
| 5 | |||
| 1 | 2001-01-17 Dave Love <fx@gnu.org> | 6 | 2001-01-17 Dave Love <fx@gnu.org> |
| 2 | 7 | ||
| 3 | * termcap.src: New version from http://www.tuxedo.org/~esr/terminfo/. | 8 | * termcap.src: New version from http://www.tuxedo.org/~esr/terminfo/. |
| @@ -1,5 +1,5 @@ | |||
| 1 | Debugging GNU Emacs | 1 | Debugging GNU Emacs |
| 2 | Copyright (c) 1985, 2000 Free Software Foundation, Inc. | 2 | Copyright (c) 1985, 2000, 2001 Free Software Foundation, Inc. |
| 3 | 3 | ||
| 4 | Permission is granted to anyone to make or distribute verbatim copies | 4 | Permission is granted to anyone to make or distribute verbatim copies |
| 5 | of this document as received, in any medium, provided that the | 5 | of this document as received, in any medium, provided that the |
| @@ -12,7 +12,21 @@ Copyright (c) 1985, 2000 Free Software Foundation, Inc. | |||
| 12 | under the above conditions, provided also that they | 12 | under the above conditions, provided also that they |
| 13 | carry prominent notices stating who last changed them. | 13 | carry prominent notices stating who last changed them. |
| 14 | 14 | ||
| 15 | ** Some useful techniques | 15 | [People who debug Emacs on Windows using native Windows debuggers |
| 16 | should read the Windows-specific section near the end of this | ||
| 17 | document.] | ||
| 18 | |||
| 19 | It is a good idea to run Emacs under GDB (or some other suitable | ||
| 20 | debugger) *all the time*. Then, when Emacs crashes, you will be able | ||
| 21 | to debug the live process, not just a core dump. (This is especially | ||
| 22 | important on systems which don't support core files, and instead print | ||
| 23 | just the registers and some stack addresses.) | ||
| 24 | |||
| 25 | If Emacs hangs, or seems to be stuck in some infinite loop, typing | ||
| 26 | "kill -TSTP PID", where PID is the Emacs process ID, will cause GDB to | ||
| 27 | kick in, provided that you run under GDB. | ||
| 28 | |||
| 29 | ** Getting control to the debugger | ||
| 16 | 30 | ||
| 17 | `Fsignal' is a very useful place to stop in. | 31 | `Fsignal' is a very useful place to stop in. |
| 18 | All Lisp errors go through there. | 32 | All Lisp errors go through there. |
| @@ -37,6 +51,9 @@ to GDB immediately if you type this command first: | |||
| 37 | 51 | ||
| 38 | handle 2 stop | 52 | handle 2 stop |
| 39 | 53 | ||
| 54 | By default the src/.gdbinit file in the Emacs distribution arranges | ||
| 55 | for SIGINT to be passed to Emacs. You can type C-z, which generates | ||
| 56 | SIGTSTP, to cause GDB to regain control. | ||
| 40 | 57 | ||
| 41 | ** Examining Lisp object values. | 58 | ** Examining Lisp object values. |
| 42 | 59 | ||
| @@ -45,9 +62,16 @@ fatal error, you can use the GDB command `pr'. First print the value | |||
| 45 | in the ordinary way, with the `p' command. Then type `pr' with no | 62 | in the ordinary way, with the `p' command. Then type `pr' with no |
| 46 | arguments. This calls a subroutine which uses the Lisp printer. | 63 | arguments. This calls a subroutine which uses the Lisp printer. |
| 47 | 64 | ||
| 48 | If you can't use this command, either because the process can't run | 65 | Note: It is not a good idea to try `pr' if you know that Emacs is in |
| 49 | a subroutine or because the data is invalid, you can fall back on | 66 | deep trouble: its stack smashed (e.g., if it encountered SIGSEGV due |
| 50 | lower-level commands. | 67 | to stack overflow), or crucial data structures, such as `obarray', |
| 68 | corrupted, etc. In such cases, the Emacs subroutine called by `pr' | ||
| 69 | might make more damage, like overwrite some data that is important for | ||
| 70 | debugging the original problem. | ||
| 71 | |||
| 72 | If you can't use `pr' command, either because the process can't run a | ||
| 73 | subroutine or because the data is invalid or Emacs already got a fatal | ||
| 74 | signal, you can fall back on lower-level commands. | ||
| 51 | 75 | ||
| 52 | Use the `xtype' command to print out the data type of the last data | 76 | Use the `xtype' command to print out the data type of the last data |
| 53 | value. Once you know the data type, use the command that corresponds | 77 | value. Once you know the data type, use the command that corresponds |
| @@ -65,9 +89,201 @@ Each x... command prints some information about the value, and | |||
| 65 | produces a GDB value (subsequently available in $) through which you | 89 | produces a GDB value (subsequently available in $) through which you |
| 66 | can get at the rest of the contents. | 90 | can get at the rest of the contents. |
| 67 | 91 | ||
| 68 | In general, most of the rest of the contents will be addition Lisp | 92 | In general, most of the rest of the contents will be additional Lisp |
| 69 | objects which you can examine in turn with the x... commands. | 93 | objects which you can examine in turn with the x... commands. |
| 70 | 94 | ||
| 95 | Even with a live process, these x... commands are useful for | ||
| 96 | examining the fields in a buffer, window, process, frame or marker. | ||
| 97 | Here's an example using concepts explained in the node "Value History" | ||
| 98 | of the GDB manual to print the variable frame from this line in | ||
| 99 | xmenu.c: | ||
| 100 | |||
| 101 | buf.frame_or_window = frame; | ||
| 102 | |||
| 103 | First, use these commands: | ||
| 104 | |||
| 105 | cd src | ||
| 106 | gdb emacs | ||
| 107 | b xmenu.c:1296 | ||
| 108 | r -q | ||
| 109 | |||
| 110 | Then type C-x 5 2 to create a new frame, and it hits the breakpoint: | ||
| 111 | |||
| 112 | (gdb) p frame | ||
| 113 | $1 = 1077872640 | ||
| 114 | (gdb) xtype | ||
| 115 | Lisp_Vectorlike | ||
| 116 | PVEC_FRAME | ||
| 117 | (gdb) xframe | ||
| 118 | $2 = (struct frame *) 0x3f0800 | ||
| 119 | (gdb) p *$ | ||
| 120 | $3 = { | ||
| 121 | size = 536871989, | ||
| 122 | next = 0x366240, | ||
| 123 | name = 809661752, | ||
| 124 | [...] | ||
| 125 | } | ||
| 126 | (gdb) p $3->name | ||
| 127 | $4 = 809661752 | ||
| 128 | |||
| 129 | Now we can use `pr' to print the name of the frame: | ||
| 130 | |||
| 131 | (gdb) pr | ||
| 132 | "emacs@steenrod.math.nwu.edu" | ||
| 133 | |||
| 134 | The Emacs C code heavily uses macros defined in lisp.h. So suppose | ||
| 135 | we want the address of the l-value expression near the bottom of | ||
| 136 | `add_command_key' from keyboard.c: | ||
| 137 | |||
| 138 | XVECTOR (this_command_keys)->contents[this_command_key_count++] = key; | ||
| 139 | |||
| 140 | XVECTOR is a macro, and therefore GDB does not know about it. | ||
| 141 | GDB cannot evaluate "p XVECTOR (this_command_keys)". | ||
| 142 | |||
| 143 | However, you can use the xvector command in GDB to get the same | ||
| 144 | result. Here is how: | ||
| 145 | |||
| 146 | (gdb) p this_command_keys | ||
| 147 | $1 = 1078005760 | ||
| 148 | (gdb) xvector | ||
| 149 | $2 = (struct Lisp_Vector *) 0x411000 | ||
| 150 | 0 | ||
| 151 | (gdb) p $->contents[this_command_key_count] | ||
| 152 | $3 = 1077872640 | ||
| 153 | (gdb) p &$ | ||
| 154 | $4 = (int *) 0x411008 | ||
| 155 | |||
| 156 | Here's a related example of macros and the GDB `define' command. | ||
| 157 | There are many Lisp vectors such as `recent_keys', which contains the | ||
| 158 | last 100 keystrokes. We can print this Lisp vector | ||
| 159 | |||
| 160 | p recent_keys | ||
| 161 | pr | ||
| 162 | |||
| 163 | But this may be inconvenient, since `recent_keys' is much more verbose | ||
| 164 | than `C-h l'. We might want to print only the last 10 elements of | ||
| 165 | this vector. `recent_keys' is updated in keyboard.c by the command | ||
| 166 | |||
| 167 | XVECTOR (recent_keys)->contents[recent_keys_index] = c; | ||
| 168 | |||
| 169 | So we define a GDB command `xvector-elts', so the last 10 keystrokes | ||
| 170 | are printed by | ||
| 171 | |||
| 172 | xvector-elts recent_keys recent_keys_index 10 | ||
| 173 | |||
| 174 | where you can define xvector-elts as follows: | ||
| 175 | |||
| 176 | define xvector-elts | ||
| 177 | set $i = 0 | ||
| 178 | p $arg0 | ||
| 179 | xvector | ||
| 180 | set $foo = $ | ||
| 181 | while $i < $arg2 | ||
| 182 | p $foo->contents[$arg1-($i++)] | ||
| 183 | pr | ||
| 184 | end | ||
| 185 | document xvector-elts | ||
| 186 | Prints a range of elements of a Lisp vector. | ||
| 187 | xvector-elts v n i | ||
| 188 | prints `i' elements of the vector `v' ending at the index `n'. | ||
| 189 | end | ||
| 190 | |||
| 191 | ** Getting Lisp-level backtrace information within GDB | ||
| 192 | |||
| 193 | The most convenient way is to use the `xbacktrace' command. | ||
| 194 | |||
| 195 | If that doesn't work (e.g., because the `backtrace_list' structure is | ||
| 196 | corrupted), type "bt" at the GDB prompt, to produce the C-level | ||
| 197 | backtrace, and look for stack frames that call Ffuncall. Select them | ||
| 198 | one by one in GDB, by typing "up N", where N is the appropriate number | ||
| 199 | of frames to go up, and in each frame that calls Ffuncall type this: | ||
| 200 | |||
| 201 | p *args | ||
| 202 | pr | ||
| 203 | |||
| 204 | This will print the name of the Lisp function called by that level | ||
| 205 | of function calling. | ||
| 206 | |||
| 207 | By printing the remaining elements of args, you can see the argument | ||
| 208 | values. Here's how to print the first argument: | ||
| 209 | |||
| 210 | p args[1] | ||
| 211 | pr | ||
| 212 | |||
| 213 | If you do not have a live process, you can use xtype and the other | ||
| 214 | x... commands such as xsymbol to get such information, albeit less | ||
| 215 | conveniently. For example: | ||
| 216 | |||
| 217 | p *args | ||
| 218 | xtype | ||
| 219 | |||
| 220 | and, assuming that "xtype" says that args[0] is a symbol: | ||
| 221 | |||
| 222 | xsymbol | ||
| 223 | |||
| 224 | ** Debugging what happens while preloading and dumping Emacs | ||
| 225 | |||
| 226 | Type `gdb temacs' and start it with `r -batch -l loadup dump'. | ||
| 227 | |||
| 228 | If temacs actually succeeds when running under GDB in this way, do not | ||
| 229 | try to run the dumped Emacs, because it was dumped with the GDB | ||
| 230 | breakpoints in it. | ||
| 231 | |||
| 232 | ** Debugging `temacs' | ||
| 233 | |||
| 234 | Debugging `temacs' is useful when you want to establish whether a | ||
| 235 | problem happens in an undumped Emacs. To run `temacs' under a | ||
| 236 | debugger, type "gdb temacs", then start it with `r -batch -l loadup'. | ||
| 237 | |||
| 238 | ** If you encounter X protocol errors | ||
| 239 | |||
| 240 | Try evaluating (x-synchronize t). That puts Emacs into synchronous | ||
| 241 | mode, where each Xlib call checks for errors before it returns. This | ||
| 242 | mode is much slower, but when you get an error, you will see exactly | ||
| 243 | which call really caused the error. | ||
| 244 | |||
| 245 | ** If the symptom of the bug is that Emacs fails to respond | ||
| 246 | |||
| 247 | Don't assume Emacs is `hung'--it may instead be in an infinite loop. | ||
| 248 | To find out which, make the problem happen under GDB and stop Emacs | ||
| 249 | once it is not responding. (If Emacs is using X Windows directly, you | ||
| 250 | can stop Emacs by typing C-z at the GDB job.) Then try stepping with | ||
| 251 | `step'. If Emacs is hung, the `step' command won't return. If it is | ||
| 252 | looping, `step' will return. | ||
| 253 | |||
| 254 | If this shows Emacs is hung in a system call, stop it again and | ||
| 255 | examine the arguments of the call. If you report the bug, it is very | ||
| 256 | important to state exactly where in the source the system call is, and | ||
| 257 | what the arguments are. | ||
| 258 | |||
| 259 | If Emacs is in an infinite loop, try to determine where the loop | ||
| 260 | starts and ends. The easiest way to do this is to use the GDB command | ||
| 261 | `finish'. Each time you use it, Emacs resumes execution until it | ||
| 262 | exits one stack frame. Keep typing `finish' until it doesn't | ||
| 263 | return--that means the infinite loop is in the stack frame which you | ||
| 264 | just tried to finish. | ||
| 265 | |||
| 266 | Stop Emacs again, and use `finish' repeatedly again until you get back | ||
| 267 | to that frame. Then use `next' to step through that frame. By | ||
| 268 | stepping, you will see where the loop starts and ends. Also, examine | ||
| 269 | the data being used in the loop and try to determine why the loop does | ||
| 270 | not exit when it should. | ||
| 271 | |||
| 272 | ** If certain operations in Emacs are slower than they used to be, here | ||
| 273 | is some advice for how to find out why. | ||
| 274 | |||
| 275 | Stop Emacs repeatedly during the slow operation, and make a backtrace | ||
| 276 | each time. Compare the backtraces looking for a pattern--a specific | ||
| 277 | function that shows up more often than you'd expect. | ||
| 278 | |||
| 279 | If you don't see a pattern in the C backtraces, get some Lisp | ||
| 280 | backtrace information by typing "xbacktrace" or by looking at Ffuncall | ||
| 281 | frames (see above), and again look for a pattern. | ||
| 282 | |||
| 283 | When using X, you can stop Emacs at any time by typing C-z at GDB. | ||
| 284 | When not using X, you can do this with C-g. On non-Unix platforms, | ||
| 285 | such as MS-DOS, you might need to press C-BREAK instead. | ||
| 286 | |||
| 71 | ** If GDB does not run and your debuggers can't load Emacs. | 287 | ** If GDB does not run and your debuggers can't load Emacs. |
| 72 | 288 | ||
| 73 | On some systems, no debugger can load Emacs with a symbol table, | 289 | On some systems, no debugger can load Emacs with a symbol table, |
| @@ -117,3 +333,140 @@ An easy way to see if too much text is being redrawn on a terminal is to | |||
| 117 | evaluate `(setq inverse-video t)' before you try the operation you think | 333 | evaluate `(setq inverse-video t)' before you try the operation you think |
| 118 | will cause too much redrawing. This doesn't refresh the screen, so only | 334 | will cause too much redrawing. This doesn't refresh the screen, so only |
| 119 | newly drawn text is in inverse video. | 335 | newly drawn text is in inverse video. |
| 336 | |||
| 337 | |||
| 338 | ** Debugging LessTif | ||
| 339 | |||
| 340 | If you encounter bugs whereby Emacs built with LessTif grabs all mouse | ||
| 341 | and keyboard events, or LessTif menus behave weirdly, it might be | ||
| 342 | helpful to set the `DEBUGSOURCES' and `DEBUG_FILE' environment | ||
| 343 | variables, so that one can see what LessTif was doing at this point. | ||
| 344 | For instance | ||
| 345 | |||
| 346 | export DEBUGSOURCES="RowColumn.c MenuShell.c MenuUtil.c" | ||
| 347 | export DEBUG_FILE=/usr/tmp/LESSTIF_TRACE | ||
| 348 | |||
| 349 | causes LessTif to print traces from the three named source files to a | ||
| 350 | file in `/usr/tmp' (that file can get pretty large). | ||
| 351 | |||
| 352 | Running GDB from another terminal could also help with such problems. | ||
| 353 | You can arrange for GDB to run on one machine, with the Emacs display | ||
| 354 | appearing on another. Then, when the bug happens, you can go back to | ||
| 355 | the machine where you started GDB and use the debugger from there. | ||
| 356 | |||
| 357 | |||
| 358 | ** Running Emacs with Purify | ||
| 359 | |||
| 360 | Emacs compiled with Purify won't run without some hacking. Here are | ||
| 361 | some of the changes you might find necessary (SYSTEM-NAME and | ||
| 362 | MACHINE-NAME are the names of your OS- and CPU-specific headers in the | ||
| 363 | subdirectories of `src'): | ||
| 364 | |||
| 365 | - In src/s/SYSTEM-NAME.h add "#define SYSTEM_MALLOC". | ||
| 366 | |||
| 367 | - In src/m/MACHINE-NAME.h add "#define CANNOT_DUMP" and | ||
| 368 | "#define CANNOT_UNEXEC". | ||
| 369 | |||
| 370 | - Configure with a different --prefix= option. If you use GCC, | ||
| 371 | version 2.7.2 is preferred, as Purify works a lot better with it | ||
| 372 | than with 2.95 or later versions. | ||
| 373 | |||
| 374 | - Type "make" then "make -k install". You might need to run | ||
| 375 | "make -k install twice. | ||
| 376 | |||
| 377 | - cd src; purify -chain-length=40 gcc <link command line for temacs> | ||
| 378 | |||
| 379 | - cd ..; src/temacs | ||
| 380 | |||
| 381 | Note that Purify might print lots of false alarms for bitfields used | ||
| 382 | by Emacs in some data structures. If you want to get rid of the false | ||
| 383 | alarms, you will have to hack the definitions of these data structures | ||
| 384 | on the respective headers to remove the ":N" bitfield definitions | ||
| 385 | (which will cause each such field to use a full int). | ||
| 386 | |||
| 387 | |||
| 388 | ** Debugging problems which happen in GC | ||
| 389 | |||
| 390 | The array `last_marked' (defined on alloc.c) can be used to display | ||
| 391 | up to 500 last objects marked by the garbage collection process. The | ||
| 392 | variable `last_marked_index' holds the index into the `last_marked' | ||
| 393 | array one place beyond where the very last marked object is stored. | ||
| 394 | |||
| 395 | The single most important goal in debugging GC problems is to find the | ||
| 396 | Lisp data structure that got corrupted. This is not easy since GC | ||
| 397 | changes the tag bits and relocates strings which make it hard to look | ||
| 398 | at Lisp objects with commands such as `pr'. It is sometimes necessary | ||
| 399 | to convert Lisp_Object variables into pointers to C struct's manually. | ||
| 400 | Use the `last_marked' array and the source to reconstruct the sequence | ||
| 401 | that objects were marked. | ||
| 402 | |||
| 403 | Once you discover the corrupted Lisp object or data structure, it is | ||
| 404 | useful to look at it in a fresh session and compare its contents with | ||
| 405 | a session that you are debugging. | ||
| 406 | |||
| 407 | |||
| 408 | ** Some suggestions for debugging on MS Windows: | ||
| 409 | |||
| 410 | (written by Marc Fleischeuers, Geoff Voelker and Andrew Innes) | ||
| 411 | |||
| 412 | To debug emacs with Microsoft Visual C++, you either start emacs from | ||
| 413 | the debugger or attach the debugger to a running emacs process. To | ||
| 414 | start emacs from the debugger, you can use the file bin/debug.bat. The | ||
| 415 | Microsoft Developer studio will start and under Project, Settings, | ||
| 416 | Debug, General you can set the command-line arguments and emacs' | ||
| 417 | startup directory. Set breakpoints (Edit, Breakpoints) at Fsignal and | ||
| 418 | other functions that you want to examine. Run the program (Build, | ||
| 419 | Start debug). Emacs will start and the debugger will take control as | ||
| 420 | soon as a breakpoint is hit. | ||
| 421 | |||
| 422 | You can also attach the debugger to an already running emacs process. | ||
| 423 | To do this, start up the Microsoft Developer studio and select Build, | ||
| 424 | Start debug, Attach to process. Choose the Emacs process from the | ||
| 425 | list. Send a break to the running process (Debug, Break) and you will | ||
| 426 | find that execution is halted somewhere in user32.dll. Open the stack | ||
| 427 | trace window and go up the stack to w32_msg_pump. Now you can set | ||
| 428 | breakpoints in Emacs (Edit, Breakpoints). Continue the running Emacs | ||
| 429 | process (Debug, Step out) and control will return to Emacs, until a | ||
| 430 | breakpoint is hit. | ||
| 431 | |||
| 432 | To examine the contents of a lisp variable, you can use the function | ||
| 433 | 'debug_print'. Right-click on a variable, select QuickWatch (it has | ||
| 434 | an eyeglass symbol on its button in the toolbar), and in the text | ||
| 435 | field at the top of the window, place 'debug_print(' and ')' around | ||
| 436 | the expression. Press 'Recalculate' and the output is sent to stderr, | ||
| 437 | and to the debugger via the OutputDebugString routine. The output | ||
| 438 | sent to stderr should be displayed in the console window that was | ||
| 439 | opened when the emacs.exe executable was started. The output sent to | ||
| 440 | the debugger should be displayed in the 'Debug' pane in the Output | ||
| 441 | window. If Emacs was started from the debugger, a console window was | ||
| 442 | opened at Emacs' startup; this console window also shows the output of | ||
| 443 | 'debug_print'. | ||
| 444 | |||
| 445 | For example, start and run Emacs in the debugger until it is waiting | ||
| 446 | for user input. Then click on the `Break' button in the debugger to | ||
| 447 | halt execution. Emacs should halt in `ZwUserGetMessage' waiting for | ||
| 448 | an input event. Use the `Call Stack' window to select the procedure | ||
| 449 | `w32_msp_pump' up the call stack (see below for why you have to do | ||
| 450 | this). Open the QuickWatch window and enter | ||
| 451 | "debug_print(Vexec_path)". Evaluating this expression will then print | ||
| 452 | out the contents of the lisp variable `exec-path'. | ||
| 453 | |||
| 454 | If QuickWatch reports that the symbol is unknown, then check the call | ||
| 455 | stack in the `Call Stack' window. If the selected frame in the call | ||
| 456 | stack is not an Emacs procedure, then the debugger won't recognize | ||
| 457 | Emacs symbols. Instead, select a frame that is inside an Emacs | ||
| 458 | procedure and try using `debug_print' again. | ||
| 459 | |||
| 460 | If QuickWatch invokes debug_print but nothing happens, then check the | ||
| 461 | thread that is selected in the debugger. If the selected thread is | ||
| 462 | not the last thread to run (the "current" thread), then it cannot be | ||
| 463 | used to execute debug_print. Use the Debug menu to select the current | ||
| 464 | thread and try using debug_print again. Note that the debugger halts | ||
| 465 | execution (e.g., due to a breakpoint) in the context of the current | ||
| 466 | thread, so this should only be a problem if you've explicitly switched | ||
| 467 | threads. | ||
| 468 | |||
| 469 | It is also possible to keep appropriately masked and typecast lisp | ||
| 470 | symbols in the Watch window, this is more convenient when steeping | ||
| 471 | though the code. For instance, on entering apply_lambda, you can | ||
| 472 | watch (struct Lisp_Symbol *) (0xfffffff & args[0]). | ||