summaryrefslogtreecommitdiff
path: root/HACKING
diff options
context:
space:
mode:
Diffstat (limited to 'HACKING')
-rw-r--r--HACKING298
1 files changed, 298 insertions, 0 deletions
diff --git a/HACKING b/HACKING
new file mode 100644
index 00000000..e669b7a1
--- /dev/null
+++ b/HACKING
@@ -0,0 +1,298 @@
+Intro...
+
+Window managers have a few ways in which they are significantly different
+from other applications. This file, combined with the code overview in
+doc/code-overview.txt, should hopefully provide a series of relatively
+quick pointers (hopefully only a few minutes each) to some of the places
+one can look to orient themselves and get started. Some of this will be
+general to window managers on X, much will be specific to Marco, and
+there's probably some information that's common to programs in general but
+is nonetheless useful.
+
+Overview
+ Administrative issues
+ Minimal Building/Testing Environment
+ Relevant standards and X properties
+ Debugging and testing
+ Debugging logs
+ Adding information to the log
+ Valgrind
+ Testing Utilities
+ Technical gotchas to keep in mind
+ Other important reading
+ Extra reading
+ Ideas for tasks to work on
+
+
+Administrative issues
+ Don't commit substantive code in here without asking [email protected].
+ Adding translations, no-brainer typo fixes, etc. is fine.
+
+ The code could use cleanup in a lot of places, feel free to do so.
+
+ See http://developer.gnome.org/dotplan/for_maintainers.html for
+ information on how to make a release. The only difference from those
+ instructions is that the minor version number of a Marco release
+ should always be a number from the Fibonacci sequence.
+
+Minimal Building/Testing Environment
+ You do not need to _install_ a development version of Marco to
+ build, run and test it; you can run it from some temporary
+ directory. Also, you do not need to build all of Mate in order to
+ build a development version of Marco -- odds are, you may be able
+ to build marco from CVS without building any other modules.
+
+ As long as you have gtk+ >= 2.10 and MateConf with your distro (gtk+ >=
+ 2.6 if you manually revert the change from bug 348633), you should
+ be able to install your distro's development packages
+ (e.g. gtk2-devel, MateConf2-devel, startup-notification-devel on
+ Fedora; also, remember to install the mate-common package which is
+ needed for building cvs versions of Mate modules like Marco) as
+ well as the standard development tools (gcc, autoconf, automake,
+ pkg-config, intltool, and libtool) and be ready to build and test
+ Marco. Steps to do so:
+
+ $ svn checkout http://svn.gnome.org/svn/marco/trunk marco
+ $ cd marco
+ $ ./autogen.sh --prefix /usr
+ $ make
+ $ ./src/marco --replace
+
+ Again, note that you do not need to run 'make install'.
+
+Relevant standards and X properties
+ There are two documents that describe some basics about how window
+ managers should behave: the ICCCM (Inter-Client Communication Conventions
+ Manual) and EWMH (Extended Window Manager Hints). You can find these at
+ the following locations:
+ ICCCM - http://tronche.com/gui/x/icccm/
+ EWMH - :pserver:[email protected]:/cvs
+ The ICCCM is usually available in RPM or DEB format as well. There is
+ actually an online version of the EWMH, but it is almost always woefully
+ out of date. Just get it from cvs with these commands (the backslash
+ means include the stuff from the next line):
+ cvs -d :pserver:[email protected]:/cvs/icccm-extensions login
+ cvs -d :pserver:[email protected]:/cvs/icccm-extensions \
+ checkout wm-spec
+
+ DO NOT GO AND READ THOSE THINGS. THEY ARE REALLY, REALLY BORING.
+
+ If you do, you'll probably end up catching up on your sleep instead of
+ hacking on Marco. ;-) Instead, just look at the table of contents and
+ glance at a page or two to get an idea of what's in there. Then only
+ refer to it if you see something weird in the code and you don't know
+ what it is but has some funny looking name like you see in one of those
+ two documents.
+
+ You can refer to the COMPLIANCE file for additional information on these
+ specifications and Marco's compliance therewith.
+
+ One of the major things those documents cover that are useful to learn
+ about immediately are X properties. The right way to learn about those,
+ though, is through hand on experimentation with the xprop command (and
+ then look up things you find from xprop in those two manuals if you're
+ curious enough). First, try running
+ xprop
+ in a terminal and click on one of the windows on your screen. That gives
+ you the x properties for that window. Look through them and get a basic
+ idea of what's there for kicks. Note that you can get rid of some of the
+ verboseness by grepping out the _NET_WM_ICON stuff, i.e.
+ xprop | grep -v _NET_WM_ICON
+ Next, try running
+ xprop -root
+ in a terminal. There's all the properties of the root window (which you
+ can think of as the "main" Xserver window). You can also manually
+ specify individual windows that you want the properties of with
+ xprop -id <id>
+ if you know the id of the window in question. You can get the id of a
+ given window by either running xwininfo, e.g.
+ xwininfo | grep "Window id" | cut -f 4 -d ' '
+ or by looking at the _NET_CLIENT_STACKING property of the root
+ window. Finally, it can also be useful to add "-spy" (without the
+ quotes) to the xprop command to get it to continually monitor that
+ window and report any changes to you.
+
+Debugging information
+ Trying to run a window manager under a typical debugger, such as gdb,
+ unfortunately just doesn't work very well. So, we have to resort to
+ other methods.
+
+ Debugging logs
+
+ First, note that you can start a new version of marco to replace the
+ existing one by running
+ marco --replace
+ (which also comes in handy in the form "./src/marco --replace" when
+ trying to quickly test a small change while hacking on marco without
+ doing a full "make install", though I'm going off topic...) This will
+ allow you to see any warnings printed at the terminal. Sometimes it's
+ useful to have these directed to a logfile instead, which you can do by
+ running
+ MARCO_USE_LOGFILE=1 marco --replace
+ The logfile it uses will be printed in the terminal. Sometimes, it's
+ useful to get more information than just warnings. You can set
+ MARCO_VERBOSE to do that, like so:
+ MARCO_VERBOSE=1 MARCO_USE_LOGFILE=1 marco --replace
+ (note that MARCO_VERBOSE=1 can be problematic without
+ MARCO_USE_LOGFILE=1; avoid it unless running in from something that
+ won't be managed by the new Marco--see bug 305091 for more details).
+ There are also other flags, such as MARCO_DEBUG, most of which I
+ haven't tried and don't know what they do. Go to the source code
+ directory and run
+ grep "MARCO_" * | grep getenv
+ to find out what the other ones are.
+
+ Adding information to the log
+
+ Since we can't single step with a debugger, we often have to fall back to
+ the primitive method of getting information we want to know: adding
+ "print" statements. Marco has a fairly structured way to do this,
+ using the functions meta_warning, meta_topic, and meta_verbose. All
+ three have the same basic format as printf, except that meta_topic also
+ takes a leading enumeration parameter to specify the type of message
+ being shown (makes it easier for grepping in a verbose log). You'll find
+ tons of examples in the source code if you need them; just do a quick
+ grep or look in most any file. Note that meta_topic and meta_verbose
+ messages only appear if verbosity is turned on. I tend to frequently add
+ temporary meta_warning statements (or switch meta_topic or meta_verbose
+ ones to meta_warning ones) and then undo the changes once I've learned
+ the info that I needed.
+
+ There is also a meta_print_backtrace (which again is only active if
+ verbosity is turned on) that can also be useful if you want to learn how
+ a particular line of code gets called. And, of course, there's always
+ g_assert if you want to make sure some section isn't executed (or isn't
+ executed under certain conditions).
+
+ Valgrind
+
+ Valgrind is awesome for finding memory leaks or corruption and
+ uninitialized variables. But I also tend to use it in a non-traditional
+ way as a partial substitute for a normal debugger: it can provide me with
+ a stack trace of where marco is crashing if I made a change that
+ caused it to do so, which is one of the major uses of debuggers. (And,
+ what makes it cooler than a debugger is that there will also often be
+ warnings pinpointing the cause of the crash from either some kind of
+ simple memory corruption or an uninitialized variable). Sometimes, when
+ I merely want to know what is calling a particular function I'll just
+ throw in an "int i; printf("%d\n", i);" just because valgrind will give
+ me a full stacktrace whenever it sees that uninitialized variable being
+ used (yes, I could use meta_print_backtrace, but that means I have to
+ turn verbosity on).
+
+ To run marco under valgrind, use options typical for any Mate
+ program, such as
+ valgrind --log-file=marco.log --tool=memcheck --num-callers=48 \
+ --leak-check=yes --leak-resolution=high --show-reachable=yes \
+ ./src/marco --replace
+ where, again, the backslashes mean to join all the stuff on the following
+ line with the previous one.
+
+ However, there is a downside. Things run a little bit slowly, and it
+ appears that you'll need about 1.5GB of ram, which unfortunately prevents
+ most people from trying this.
+
+ Testing Utilities
+
+ src/run-marco.sh
+ The script src/run-marco.sh is useful to hack on the window manager.
+ It runs marco in an Xnest. e.g.:
+ CLIENTS=3 ./run-marco.sh
+ or
+ DEBUG=memprof ./run-marco.sh
+ or
+ DEBUG_TEST=1 ./run-marco-sh
+ or whatever.
+
+ marco-message
+ The tool marco-message can be used as follows:
+ marco-message reload-theme
+ marco-message restart
+ marco-message enable-keybindings
+ marco-message disable-keybindings
+ The first of these is useful for testing themes, the second is just
+ another way (besides the --restart flag to marco itself) of
+ restarting marco, and the third is useful for testing Marco when
+ running it under an Xnest (typically, the Marco under the Xnest
+ wouldn't get keybinding notifications--making keyboard navigation not
+ work--but if you disable the keybindings for the global Marco then
+ the Marco under the Xnest can then get those keybinding notifications).
+
+ marco-window-demo
+ marco-window-demo is good for trying behavior of various kinds
+ of window without launching a full desktop.
+
+Technical gotchas to keep in mind
+ Files that include gdk.h or gtk.h are not supposed to include
+ display.h or window.h or other core files. Files in the core
+ (display.[hc], window.[hc]) are not supposed to include gdk.h or
+ gtk.h. Reasons:
+
+ "Basically you don't want GDK most of the time. It adds
+ abstractions that cause problems, because they aren't designed to
+ be used in a WM where we do weird stuff (display grabs, and just
+ being the WM). At best GDK adds inefficiency, at worst it breaks
+ things in weird ways where you have to be a GDK guru to figure
+ them out. Owen also told me that they didn't want to start adding
+ a lot of hacks to GDK to let a WM use it; we both agreed back in
+ the mists of time that marco would only use it for the "UI"
+ bits as it does.
+
+ Having the split in the source code contains and makes very clear
+ the interface between the WM and GDK/GTK. This keeps people from
+ introducing extra GDK/GTK usage when it isn't needed or
+ appropriate. Also, it speeds up the compilation a bit, though this
+ was perhaps more relevant 5 years ago than it is now.
+
+ There was also a very old worry that the GDK stuff might have to
+ be in a separate process to work right; that turned out to be
+ untrue. Though who knows what issues the CM will introduce."
+
+ Remember that strings stored in X properties are not in UTF-8, and they
+ have to end up in UTF-8 before we try putting them through Pango.
+
+ If you make any X request involving a client window, you have to
+ meta_error_trap_push() around the call; this is not necessary for X
+ requests on the frame windows.
+
+ Remember that not all windows have frames, and window->frame can be NULL.
+
+Other important reading & where to get started
+ Extra reading
+
+ There are some other important things to read to get oriented as well.
+ These are:
+ http://pobox.com/~hp/features.html
+ rationales.txt
+ doc/code-overview.txt
+
+ It pays to read http://pobox.com/~hp/features.html in order
+ to understand the philosophy of Marco.
+
+ The rationales.txt file has two things: (1) a list of design choices with
+ links in the form of bugzilla bugs that discuss the issue, and (2) a list
+ outstanding bug categories, each of which is tracked by a particular
+ tracker bug in bugzilla from which you can find several closely related
+ bug reports.
+
+ doc/code-overview.txt provides a fairly good overview of the code,
+ including coverage of the function of the various files, the main
+ structures and their relationships, and places to start looking in the
+ code tailored to general categories of tasks.
+
+ Ideas for tasks to work on
+
+ There are a variety of things you could work on in the code. You may
+ have ideas of your own, but in case you don't, let me provide a list of
+ ideas you could choose from:
+
+ If you're ambitious, there's a list of things Havoc made that he'd really
+ like to see tackled, which you can find at
+ http://log.ometer.com/2004-05.html. Be sure to double check with someone
+ to make sure the item is still relevant if you're interested in one of
+ these. Another place to look for ideas, of course, is bugzilla. One can
+ just do queries and look for things that look fixable.
+
+ However, perhaps the best way of getting ideas of related tasks to work
+ on, is to look at the second half of the rationales.txt file, which tries
+ to group bugs by type.