Showing posts with label programming. Show all posts
Showing posts with label programming. Show all posts

2011-12-22

sauron: keeping an eye on what's going on

I'm a fairly busy person, and need to keep track of a lot of things. That includes following a bunch of internal IRC channels, attending meetings, meeting deadlines and so on. But I don't want to stare at my org-mode calendar, or flip through ERC buffers all the time.

Instead, I'd like to have one little emacs frame (window) that gathers these ('events'), and transfers me to wherever the event came from when I click it - some IRC-channel in ERC, my org-calendar etc. and other inputs. Note, using Bitlbee, you can include Facebook-contacts, GoogleTalk-buddies and Twitter-tweets, … in ERC - so, you can track just about anything.

In addition, with so many inputs, I'd also like the possibility to filter out unwanted events, and generate various light/sound effects and fireworks, proportional to the priority of the event.

For all this, I wrote a little emacs-tool called Sauron that does just that. M-x sauron-start pops up a frame that receives events, and M-x sauron-stop hides it and stops listening. It works with ERC, org, and listens for D-Bus messages; so it's pretty easy to get events from all over the place.

It's a bit of a balancing act to get all the important information while not being swamped in noise, but Sauron allows you to fine-tune it to whatever works the best for you. I've tried to have sane defaults though, so things should mostly work without too much configuration - but if you need the power, it's there. I also added some convenience functions to make it easy to get sounds and other special effects.

So - it's brand new, it is of seems-to-work-for-me-quality, and I'd like to invite others to try it out, hack it, give feedback, add new back-ends and so on – what better Christmas present to ask for!

There's documentation, examples etc. to be found in Sauron's github repository.

2011-05-16

toward balanced and colorful delimiters

Emacs has the very useful feature of blinking the corresponding left "(" when you type its partner ")" (and the same for other delimiters like "[]", "{}" etc., depending on the mode). This is very useful for programming, especially for languages like Lisp and Scheme and the like.


Further help can come from tools like autopair or paredit – although the latter is a bit too much bondage & discipline for me, many people love it.
Anyway, recently I discovered a new helper in the quest for balance in delimited universe: rainbow-delimiters. With this package, the delimiters all get different colors based on their nesting level. It works wonderfully well.
Installation is straightforward:
  • download rainbow-delimiters and put it in your load-path
  • add something like the following in your .emacs:
(when (require 'rainbow-delimiters nil 'noerror) 
  (add-hook 'scheme-mode-hook 'rainbow-delimiters-mode))
That's it – of course you'll need to do the equivalent for modes where you'd like to enable it. See the screenshot below – maybe a bit too colorful for some people, but I like it and I have found it actually useful to see the corresponding delimiters without having to move the cursor over them.


I already added some nice Zenburn colors for this to the Zenburn theme for Emacs-24, as can be seen in the screenshot.

2010-09-27

interview with Eric Ludlam (CEDET)

One of the notable new features of emacs 23.2 was the inclusion of CEDET. CEDET adds IDE-type functionality to emacs, and one only needs to read the responses to the 100th post to see the great interest in that.

The man behind CEDET is Eric Ludlam (EML), a long-time Emacs user and developer. He kindly answered the many questions we had for him. Thanks, Eric!

djcb: Eric, could you tell us a little bit about yourself? And about that fantastic hobby of yours, building siege engines?

EML: I manage a software engineering team at the MathWorks. The MathWorks are the creators of Matlab. In my spare time I maintain CEDET, the Matlab support for Emacs, and build replicas of ancient siege engines.

I've been building catapults of various types for use at the World Championship Punkin' Chunk since 1998. My team started with a traction trebuchet, then a HCW Trebuchet, then moved to Human Powered Centripetal, and finally to the torsion division with MistaBallista. As far as I know, Mista Ballista is the worlds largest farthest throwing currently functional ballista.

Most recently, I got to help demolish a building where I work by shooting stuff at it, which was a lot of fun.

djcb: How did you get involved with Emacs? Do you spend a lot of time with it?

EML: I've been hacking Emacs since version 18.54 on Ultrix because the alternative was vi. My first post (and thus contribution to Emacs) was to gnu.emacs.sources on June 6, 1992. I've used Emacs to work on C/C++ code for many years which inspired all the various parts of CEDET, but these days I don't get much coding time.

My work with Emacs and CEDET is seasonal currently. The summers are usually busy with family activities, and my falls are busy getting the catapult ready, so CEDET work usually happens in the winter.

djcb: Can you tell us a bit about the background of CEDET?

EML: I started with some really basic editors and eventually with LSE (Language Sensitive Editor) on VMS. LSE was pretty cool. When I switched OSes to Ultrix and was forced to use Emacs, and discovered you could script it, I was hooked. My first big Emacs hack was etalk, an implementation of Unix talk in Emacs.

In one of the Emacs related newsgroups, a spoof story floated around about how Emacs became sentient, and started writing code for Richard [Stallman] instead of the other way around. Since then I've always wanted to get Emacs to start writing my code for me. I wrote cparse.el, a regexp nightmare that could parse almost any C file into a sequence of highly detailed tags. The tags could be used to then generate code, and I had a cool comment writing utility, automatic prototype generation, and some navigation features. On the whole it failed for many reasons.

The concept, however, continued. CParse became the basic idea behind what is now the Semantic package in CEDET, though none of the old stuff remains beyond some echos in some SRecode utilities.

My end goal is to provide round-trip code management in Emacs. Emacs needs to be able to read your code, allow you to perform transformations in the code in an abstract way, and then write new code for you. Everything in CEDET is building toward that goal. It is taking a long time, and you can see it starting to take shape. Semantic can parse the code, COGRE can manipulate UML diagrams representing your code, and you can export diagrams into code through SRecode. Unfortunately this isn't a round-trip solution as the generated code currently should not replace existing hand-written code.

Can you tell us a bit about the CEDET-project?

EML: I maintain CEDET and field questions on the mailing list. There are several contributors who either own some tool in the "contrib" area, fix bugs, answer questions or apply patches for new features. There has always been someone to pick up the slack when I'm busy elsewhere, and I've greatly appreciated that.

The easiest (and most common) way to contribute code to CEDET is to provide support for some new language, or to create a language agnostic tool using the CEDET APIs. As with Emacs, you need to be able to assign copyright to the FSF to contribute to CEDET's core, but new language support or utilities can have a home in the contrib area as well.

djcb: CEDET is part of Emacs since 23.2. Can you tell us a bit about how that happened?

EML: I've been providing assignments for the parts of CEDET since 1996 or so. For Emacs 23.1, CEDET was at a stable and useful enough state that Chong Yidong was willing to do the work to integrate it into Emacs. My ability to get a legal release for CEDET in time for Emacs 23.1 failed, so it went into 23.2 instead. It is my understanding that CEDET's smart completion engine reached a performance and reliability point that made it desirable to have in Emacs.

Emacs currently includes the parts of CEDET needed to make EDE, the project management system, Semantic and it's user tools, and SRecode all work from a user perspective. Emacs lacks the Semantic development environment, needed for writing new language support, and COGRE, the UML diagram editing tool.

djcb: Are there plans to include those parts as well?

Yes. It is important for users with a stock Emacs to develop new languages using the missing Semantic development tools. I don't know if COGRE will ever go in, though I expect that this will be done via the new package management system [elpa].

djcb: Did you ever try IDEs such as Eclipse? How do you think CEDET stacks up against such programs?

EML: I have used Visual Studio more than Eclipse, and certainly watched demos on how these and other tools work.

These tools win over CEDET's features in that they usually integrate directly with the compiler, VM or whatever, and have very good completion engines and UIs that you can interact with.

CEDET wins in that you don't need a compiler, or even code that can compile for it to work and start providing useful completions. It can infer an awful lot from a project.

CEDET's language support structure is thus simple in comparison, and CEDET supports many more languages as a side effect. It also wins because it is in Emacs, and I've done my best to try and match the "Emacs Way". For an Emacs user, this is intuitive, but can appear quirky to outsiders.

djcb: What about other development tools for in emacs?

EML: There are a lot of language specific solutions like GCCSense, slime, JDEE, and others out there. These projects are great in that they take a language, and push it to the edge of what you can do, and the users generally love that stuff. When someone wants to do the same thing, like when CSDE started for C#, and it tried to copy JDEE, it was just that, a copy that didn't quite make it.

It is my hope that CEDET will become the target of choice for users who want to make their language support in Emacs the best. They will save a lot of time doing so as well. The same infrastructure for integrating in external tools can be used to get improved results out of CEDET, but CEDET will handle converting that into a representation that would then allow any tool built on CEDET to work. This is the same model that worked well for comint.el, and gud.el.

Yasnippet is a bit different in the way it "competes" with SRecode. My first implementation of SRecode tried recycling tempo templates, but I couldn't get it to work. In fact all the template systems I investigated fell short of what I was trying to do, so I had to roll my own, and ended up using a variant of the Google template format.

The key difference is that the goal was for SRecode to provide a series of base templates for code generation. A tool writer would then write some tool to generate code. A user would then use the tool, and say "This is great, how do I change where the { goes?"

The answer is to override the template with that detail in it without interfering with the system templates. That only works if the templates are sufficiently granular that the changed template can be simple. Template reuse needs to be high so that if your company formats your methods as:

int mymethod() { implementme() };

instead of

int mymethod() {
}

that one template change will allow this to happen for all code generated from every tool.

Thus, the audience for yasnippet and SRecode is quite different. Of course you could do yasnippet like things with SRecode if someone took the time to improve the field-editing feature in SRecode, but that has not been my focus.

djcb: Do you follow the overall Emacs development process? Are there things you would like to see changed/improved?

EML: I watch the emacs-devel mailing list, mainly to see if anything related to CEDET goes by that I can help with, or what the latest cool feature might be. My first contribution of Speedbar to Emacs in Emacs 20 helped drive some features related to overlines, boxes, and other face attributes that appeared in Emacs 21.

In the future, once CEDET and Emacs cross merge techniques are hashed out, I would expect some key parts that need performance improvements might move into C. Another part of CEDET that I'd love to see become bound closer to Emacs is mode-local.el. It tries to simulate mode-local variables and mode-local functions. This is critical in a complex system like CEDET that needs to provide a language support author with fine grained control. There are good reasons not to make what is currently implemented "the Emacs way", but it would be nice to resolve those and enable mode authors a with a more powerful way to customize the user experience.

djcb: Do you have specific plans for CEDET in the future?

EML: Here is the short list:

  • Improve Emacs/CEDET cross merging
  • Offload tag storage to an external process - needed for scalability
  • Design/define a "CEDET mode" as a way of simplifying the confusing array of distinct tools and modes that make up CEDET now.
  • Finish the smart-context menu project
  • Resolve the "code replacement" problem of parsing a block of code, transforming it, and re-creating that code in place reliably.
djcb: In addition to all these 'generic' improvements, are there specific areas where new contributors could make a difference?

EML: Supporting new "stuff" in CEDET is one big win. Stuff can be:

  • New project types under EDE to ease transition from something like Visual Studio to Emacs.
  • Language support, such as parsers, or mode overrides. Finding ways to take existing cool tools, like JDE's beanshell, or slime's inferior lisp process and allowing it to do work for CEDET is another big win.
  • Templates for code generation in new languages.

Tool writing would also be good. JDEE's author Paul Kinnucan converted many bits of JDEE to CEDET and co-designed many of CEDET's parts along the way, such as semanticdb, and that was a huge help. ECB's current maintainer Klaus has also had a big impact on the way concepts are abstracted to a tool that depends on CEDET.

Naturally, joining the mailing list and fixing reported bugs and improving the doc is also a huge help, but not as exciting as writing new code. :)

djcb: Finally, many people want to start using CEDET, but it seems they have a bit of trouble to get started. Do you have any recommendations for them?

EML: Start with the cedet.info file which has many of the common setup configurations in it. If you run into something not explained well or at all, be sure to join the mailing list and be specific about how that doc failed. Very few questions on the mailing list refer to the doc, so the doc is rarely improved in a way that can help others.

Another good starting point is Alex Ott's article A Gentle Introduction to CEDET, which is very helpful.

Thanks a lot for your time, Eric! Wishing you a lot of success with CEDET and all your other projects!

2010-06-17

automatic pairing of brackets and quotes

Some text-editors, notably TextMate for MacOS, have a nice feature where inserting a opening ( will automatically insert the closing ), and put the cursor in between them (and does same for [], {}, and various quote-marks).

Not surprisingly, there are some implementations for emacs as well; the best one I have found so far is called autopair, which was written by João Távora. It usually does things just right. Do things 'just right' is essential for such a tool; even small annoyances can disturb your flow. Autopair tries to do whatever makes the most sense for a given mode (programming language etc.), but it can be tuned as well.

After installation, you can automatically activate it for all modes with (in your .emacs):

(require 'autopair)
(autopair-global-mode 1)

Now, evaluate this or restart emacs, and enjoy the autopairing-magic!

Except for autopairing, autopair also takes care of autocleaning; that is, if I press ( it turns that into () (the pairing part), and if I press Backspace then, it removes the whole () (the cleaning part). This makes things much less annoying if you type a pair by accident. Autopairing is the kind of thing that can get annoying quickly if it does not things exactly right – and autopair succeeds!

Another nice trick it offers is autowrapping – that is, I select a word, press ", and automatically it's turned into "word". To enable that, you need to add the following:

(setq autopair-autowrap t)

Note: you might want to see the notes below about delete-selection-mode and cua-mode.

Anyway, autopair with autowrap makes for a really smooth editing experience, I love it! There are two small issues for me though. First, when the cursor in front of some non-whitespace, I'd like autopairing not to happen, and second, somehow I can't seem to get "-autopairing to work in org-mode; of course, that could be my own fault. These things might be tunable; I haven't tried very hard yet.

delete-selection-mode

Important to mention here is that autopair is (by default) not fully compatible with delete-selection-mode. As you may know, that is the mode that causes emacs to replace the current selection with a character typed, similar to what most other programs do. I think many people have it enabled in their .emacs with something like:

(delete-selection-mode 1)

If you want to keep on using that together with autopair, add the following to your .emacs:

(put 'autopair-insert-opening 'delete-selection t)
(put 'autopair-skip-close-maybe 'delete-selection t)
(put 'autopair-insert-or-skip-quote 'delete-selection t)
(put 'autopair-extra-insert-opening 'delete-selection t)
(put 'autopair-extra-skip-close-maybe 'delete-selection t)
(put 'autopair-backspace 'delete-selection 'supersede)
(put 'autopair-newline 'delete-selection t)

But, not that that still won't give you the autowrap behavior mentioned above. For that, we can use cua-mode.

cua-mode

We discussed CUA-mode before, focusing on its nice rectangle-editing features. But CUA-mode can also be an alternative for delete-selection-mode, and it goes together more nicely with autopair; so, instead of delete-selection-mode and the put's, add the following to your .emacs:

(setq cua-enable-cua-keys nil)           ;; don't add C-x,C-c,C-v
(cua-mode t)                             ;; for rectangles, CUA is nice

See the linked CUA-mode article for the 'why' of that first line. With this change, autopair should be working smoothly, including autowrap.

further customization

As I have hinted at, autopair can be tuned for different modes, and can differentiate between it's behaviour in literal strings, code, comments etc. The default are usually sane, but if you're interested, have a look at the documentation, in particular autopair-extra-pairs and the More tricks-section in the documentation.

2009-05-18

building regular expressions

This whole entry could be summarized as 'use M-x re-builder' to build your regular expressions. But let's see if I can stretch that wisdom over a couple of lines…

For searching and replacing, regular expressions ('regexps') are a very useful tool. For example, see the entry about getting your ip-number. I am not going to explain regexps here – there are plenty of good references about them. Of course, emacs supports regexps - but it's not always so easy, compaired to e.g. Perl. I am only providing some trivial examples here, please see Steve Yegge's post on the regexp tricks possible with then-new Emacs 22 (I can't remember ever needing that kind of regexp-pr0n in real life though…)

Back to regexps - on of the issues with regexps in Elisp is that they need extra quoting, that is, lots of \-escape characters; regexps can be hard to comprehend, and this does not help… Why the extra quoting? Let's look at a simple example. Suppose we want to search for the word cat. And not category or concatenate. The regular expression would then be \bcat\b.

In Perl you could write this as /\bcat\b\/ (in Perl you specify regexps by putting them between /-characters).

Not so in Emacs-Lisp. On the Lisp-level, there are no regexps; there are only strings and only the regexp functions understand their true nature. But before the strings ever get those functions, the Lisp interpreter does what it does best: interpreting. And when it sees \b, it interprets it as the backspace-character.

To make it not do that, you'll need to pay the 'slash-tax' and write something like:

(re-search-forward "\\bcat\\b")
Things can go ugly quickly from there - think of when you need search for something with a backslash, like our regex \bcat\b itself; you'd need to do:
(re-search-forward "\\\\bcat\\\\b")

slash tax break

To make things even more interesting, in different contexts, different rules apply. The above is all about regexps in strings in Emacs-Lisp. However, things are different when you provide a string interactively.

Suppose you search through your buffer (with M-x isearch-forward-regexp or C-M-s). Now, your input is not interpreted by the Lisp interpreter (after all, it's just user input). So, you're exempt from the slash tax, and you can use \bcat\b to match, well, \bcat\b.

re-builder

So, regexps can be hard, and Emacs-Lisp makes it somewhat harder. A natural way to come up with the regular expression you need, is to use trial-and-error, and this is exactly what isearch-forward-regexp and friends do. But what about the slash-taxed regexps that you need in your Lisp code?

The answer is M-x re-builder. I am sure many people are already using it, but even if there were only one person that finds out about this through this blog-post, it'd be worth it! And this is the whole trick here: whenever you need a regexp in your code, put the kind of string it should match in a buffer, and enter M-x re-builder.

re-builder will put some quotes in the minibuffer. You type your regexp there, and it will show the matches in the buffer as you type. It even supports different regex-syntaxes. By default, re-builder will help you with the strings-in-Emacs-lisp kind of regexps; this is called the read-syntax. But you can switch to the user-input regexps with C-c TAB string RET (yes, these are called string here). There are some other possible syntaxes as well.

One final trick for re-builder is the subexpression mode, that you activate with C-c C-e (and leave with q). You can than see what subexpressions match (ie. if we can match cat, cut, cot etc., with \\bc\\(.\\)t\\b, and the subexpression would then contain the middle letter. re-builder automatically converts between the syntaxes it supports, so you could use 'string-mode' as well, bc\(.\)t\b.

2009-05-12

getting your ip-address

A friend asked me how to retrieve your IP-number in emacs; he needs it to figure out in which of various networks he lives, to update proxy settings and the like. He had found a decade-old function get-ip-address on the internet, and thought (correctly!) that it can't be that hard.

So, fortunately, it wasn't too hard to do it a bit better, esp. with all the improvements in emacs in the last ten years.

The somewhat-ugly-but-it-works solution is to use the output of the ifconfig tool:

(defun get-ip-address (&optional dev)
  "get the IP-address for device DEV (default: eth0)"
  (let ((dev (if dev dev "eth0"))) 
    (substring  ;; chop the final "\n"
      (shell-command-to-string
        (concat 
          "ifconfig " dev
          "|grep 'inet addr'|sed 's/.*inet addr:\\(\\([0-9\.]\\)*\\).*/\\1/'"))
      0 -1)))
Now, calling (get-ip-address "eth0") or (get-ip-address "lo") in your scripts will get you the IP-number. Obviously, this only works on systems that have this ifconfig, and is also vulnerable to small changes in the output. Don't even ask about IPv6.

The solution does give us a nice example of using shell-command-to-string, which is really useful function to integrate with all kinds of external tools; the difference with decade-old get=ip-address is striking.

However, we can do even better in these modern times. More recent versions of emacs provide nice networking functionality:

(defun get-ip-address (&optional dev)
  "get the IP-address for device DEV (default: eth0)"
  (let ((dev (if dev dev "eth0"))) 
    (format-network-address (car (network-interface-info dev)) t)))
All fine - but unfortunately, this does not work on Windows; there is no such thing as network-interface-info there, not even in the latest Emacs incarnations. Is there nothing else we can do on Windows? Well… we can go back to the first solution (using shell-command-to-string, and see if we can use it with Windows' ipconfig tool. Something like:
(defun get-ip-address () 
  "Win32: get the IP-address of the first network interface"
  (let ((ipconfig (shell-command-to-string "ipconfig | findstr Address"))) 
    (string-match "\\(\\([0-9]+.\\)+[0-9]+\\)" ipconfig)
    (match-string 0 ipconfig)))
The Windows version does not support choosing the interface; I'll leave that as an excercise to a reader with some more Win-fu; that same reader might also have a solution that does not involve ipconfig, but uses some Win32-API. And of course, that user is invited to help the emacs development team to add a Win32 version of network-interface-info.

2009-02-03

fancy debugging with gdb

In emacs, you can start debugging your application with M-x gdb. If you come from a Eclipse/Visual Studio-background, you may find the experience somewhat spartan -- and the Spartans are known for many things, but debugging is not one of them. Still, I have debugged that way for years, until I only recently (really!) discovered gdb-many-windows. It's simple; start gdb inside emacs as you'd do normaly (M-x gdb), and after that, call M-x gdb-many-windows. This will split your frame ('window') in six buffers ('sub-windows'), something like the following:
gdb commandslocal variables / registers
source code
stackbreakpoints
I am usually a bit skeptical about putting too many GUI-distractions between me and my code, but this is really useful! All the information I need at my fingertips. Emacs is a place full of hidden treasures.

If we look at gdb itself, and compare it with e.g. the Visual Studio-debugger, there are still many features missing, even with gdb-many-windows. Of course, one could easily dismiss fancy debuggers as leading to bad programming practices - and there is some truth in that. But I think there is real value in at least some of the features. So, it's nice to see that there is progress in this area. One example is Python scripting support. Using that, it's much easier to have gdb print something reasonable when looking at std::string-objects or GErrors. Now if only we could use Elisp instead of Python...

If you are new to gdb, I would recommend you to read the GDB Tutorial, and after that the GDB User Manual. Gdb is a very powerful tool, but it requires some learning. Just like emacs.

2009-01-31

which function is this?

As a short tip: in many of the programming modes, you can get the name of the function where your cursor is currently in using which-function-mode. You can set it globally in your .emacs, or make it mode specific using some hook, for example:
(add-hook 'c-mode-common-hook 
  (lambda ()
    (which-function-mode t)))
After you do this, the name of the current function will appear in the modeline (the status-bar).

Now, apart from the mode line, emacs also knows the concept of the header line. This is the first line of the display; it seems little used. However, if you'd like to have the function name there, maybe because the mode line is full already, see this trick on EmacsWiki (scroll down).

which-function-mode does not work for all modes; it needs some help from the major mode to figure out what counts as a function; in my emacs, the following modes work (you can check from the which-func-modes variable):

(emacs-lisp-mode c-mode c++-mode perl-mode cperl-mode python-mode makefile-mode sh-mode
 fortran-mode f90-mode ada-mode diff-mode)

I hope your own functions do fit on your screen, making which-function-mode less needed -- function should not be too long or complex. But it's still useful when reading other people's code, of course. Note, there are other ways to not loose your orientation when reading code; earlier, we discussed hideshow, which enables showing/hiding the function bodies.

2009-01-19

commenting your functions

When writing source code, it's nice to leave some comments, so others can understand what you were thinking. Of special concern is the documentation of public methods / functions -- that is, code that is designed to be used by other people. It's a far cry from Knuthian literate programming, but it's a start...

There are some systems to generate documentation (PDFs, html etc.) from these comments, such as JavaDoc, GTK-Doc and Doxygen. The idea is that your format your comments in such a way that these tools can understand them, and generate documentation from them. The details of this format are remarkably similar, at least between the systems mentioned here. Note that these are for C/C++ and Java; other languages have different systems.

I've found that I am much more likely to properly document my code when I have tools like the once discussed here. They take away enough of the boredom-factor to make me do it.

doxygen

I am mostly familiar with doxymacs, which is the system that adds support for Doxygen in emacs. In practice, this means that in doxymacs-mode, you can go to a function, press C-c d f (doxymacs-insert-function-comment), and a template with the arguments for this functions appears. For example, after doing this for frobnicate_numbers, we get:
/** 
 * 
 * 
 * @param a
 * @param b 
 * 
 * @return 
 */
int frobnicate_numbers (int a, int b);
Now, all we need to do is write some nice comments. Apart from a description and requirements for a and b, we should say something about the return value, if any values need to be freed, exceptions and so on. Note, I usually put the comments in the header file; that way, people can read the documentation by scanning the header files. Some people however prefer to put the comments in the implementation file.

Apart from the doxymacs-insert-function-comment mentioned above, there are also functions to include file comments (C-c d i, doxymacs-insert-file-comment) and others; see the doxygen documentation.

To install doxygen, get the package (for debian/ubuntu users: get the doxymacs-package), and then add to your .emacs:

(add-hook 'c-mode-common-hook
  (lambda ()
    (require 'doxymacs)
    (doxymacs-mode t)
    (doxymacs-font-lock)))
Of course, after nicely commenting your functions this way, you can create documentation for your code. For some example of this, see the KDE API documentation, which uses Doxygen.

I can recommend learning those keybindings; they are great timesavers.

gtk-doc

As an alternative, popular in the GLib/GTK+-world, there is GTK-Doc, which works in a very similar way. It can be a bit tricky to set up, but the integration with DevHelp is very nice -- and DevHelp you can be integrated with emacs. Anyway, GTK-Doc also provides some integration with emacs; so can get this by installing gtk-doc-tools, and then adding to your .emacs (assuming that gtk-doc lives in your load-path, see installing packages):
(add-hook 'c-mode-common-hook
  (lambda ()
    (load "gtk-doc")))
After that you can add comments to your functions with C-x 4 h ('gtk-doc-insert') in the gtk-doc format, which is slightly different from the doxygen one. (Gtk-Doc has special support for GTK/Glib-specifics but that's beyond my scope here...)
/**
 * frobnicate_numbers:
 * @a: 
 * @b: 
 *
 * 
 *
 * Returns: 
 **/
int frobnicate_numbers (int a, int b);

other

Finally, if you're programming Java, you'll be happy to hear that there is specific support for JavaDoc-style comments when you're using the excellent JDE (Java Development Environment). I haven't used it recently though, let alone its Javadoc support. So please refer to the documentation for details.

2009-01-05

navigating through source code using tags

[Updated] I was always amazed by the way emacs gurus navigated through source code. It almost seemed like magic. They see some function call, and then with some short keyboard combo jump to another file, on the exact place where the function was defined.

The 'magic' in this case is a tag file. A tag file is a file that maintains an index of all the symbols in source code, where they are used and where they are defined. If you use grep and the like to look for things, you'll find tag files very useful.

There are different programs to create and deal with tag files; emacs ships with etags and there's also ctags. I'm not too familiar with those systems, but instead rely on GNU-Global for my tagging needs; it's available for Unix-like systems. The instructions below assume that you have installed GNU-Global.

tags from the command line

First, let's see how to create and update a tag file from the command line. GNU-Global works recursively on a directory tree; that is, you can run it in the top of your source directory, and it will then index all the files found, traversing through subdirectories. To create a tag file, go to the top of your source tree and run:
$ gtags
This will create a bunch of files (GPATH, GRTAGS, GSYMS and GTAGS) that together form your tagfile. If you have run gtags before, and only want to update for changes in your source files, run:
$ global -u
This is usually much faster than running gtags. Also note that you can run this from anywhere in your source tree. The program will locate the G*-files by itself.

After that, you can search for symbols etc from the command line; please refer to the global man page for details. However, let's see how we can do all that from within emacs.

Using GNU-Global from emacs

GNU-Global comes with support for emacs, which makes it very convenient to use. It still relies on the command line to use create / update the tagfiles though; but we can do something about that with a bit of elisp. First, we define the following function djcb-gtags-create-or-update in our .emacs:
(defun djcb-gtags-create-or-update ()
  "create or update the gnu global tag file"
  (interactive)
  (if (not (= 0 (call-process "global" nil nil nil " -p"))) ; tagfile doesn't exist?
    (let ((olddir default-directory)
          (topdir (read-directory-name  
                    "gtags: top of source tree:" default-directory)))
      (cd topdir)
      (shell-command "gtags && echo 'created tagfile'")
      (cd olddir)) ; restore   
    ;;  tagfile already exists; update it
    (shell-command "global -u && echo 'updated tagfile'")))
This function will check if there is an existing tagfile; if so, it will update it. If not, it asks where to create the tag file; you should provide the name of the top of your source directory there.

Now, we can automatically run this function whenever we open a C/C++/...-file, so we always have an up-to-date tagfile available:

(add-hook 'gtags-mode-hook 
  (lambda()
    (local-set-key (kbd "M-.") 'gtags-find-tag)   ; find a tag, also M-.
    (local-set-key (kbd "M-,") 'gtags-find-rtag)))  ; reverse tag

(add-hook 'c-mode-common-hook
  (lambda ()
    (require 'gtags)
    (gtags-mode t)
    (djcb-gtags-create-or-update)))
I've found GNU-Global fast enough to run djcb-gtags-create-or-update automatically. However, if you work with really huge code bases (for example, the linux kernel sources) it's better to use a tag file for some not-too-big sub-tree, or turn tagging off. To turn off automatic updating/creating tagging for some particular directory, you could do something like: [Update: fix elisp error, thanks Anatoly]
(add-hook 'c-mode-common-hook
  (lambda ()
    (require 'gtags)
    (gtags-mode t)
    (when (not (string-match "/usr/src/linux/" (expand-file-name default-directory)))  
      (djcb-gtags-create-or-update))))
instead of the above add-hook. You can then still run djcb-gtags-create-or-update by hand for some particular subdirectory.

usage

Now, having done all this, tagging is quite easy - and quickly through your source code is even easier. To find the definition of a function (or symbol), type M-. (Alt + dot). If your cursor is on a function name (or on other symbol), it will be the default target. Otherwise, you type the name; autocompletion is available with the Tab-key.

If you want to do the reverse, ie. finding all the uses of a certain symbol, use M-, (Alt + comma) and we get a list of locations. There are some more functions available, all starting with gtags-; see the built-in documentation for details.

2008-12-26

showing and hiding blocks of code

When I'm writing some code, I find it often useful to hide most function bodies, and only see the one I am working on. This way, I can keep the overview, and concentrate on the part I am working on. Emacs has support for showing/hiding blocks of code, using the HideShow-package. HideShow works with C/C++, Lisp, Scheme, Java, Perl, PHP, TCL, VHDL and Fortran. It also seems to work with Javascript (at least JS2).

You can enable Hide-Show for C/C++ code by adding the following to your .emacs:

(add-hook 'c-mode-common-hook
  (lambda()
    (local-set-key (kbd "C-c <right>") 'hs-show-block)
    (local-set-key (kbd "C-c <left>")  'hs-hide-block)
    (local-set-key (kbd "C-c <up>")    'hs-hide-all)
    (local-set-key (kbd "C-c <down>")  'hs-show-all)
    (hs-minor-mode t)))
You can hide or show either the current block, or the whole file. To show the former, consider a C-function:
int my_function (int a, int b)
{
 return a + b;
}
Now, when calling hs-hide-block, we get:
int my_function (int a, int b)...
HideShow has one problem: the truly bizarre default key bindings, such as 'C-c @ ESC C-s' for hs-show-all. This is the reason I am adding these alternative key bindings in the add-hook above - 'C-c' and the arrow keys; alternatively, you could use the 'Super'-key instead of C-c.

If you'd like to hide everything by default when you open a file, you can do so by adding

(hs-hide-all)
to the above hook function.

Side-note: Even though there are many keys on your keyboard, there is a finite number of easy combinations, especially when the arrow-keys are involved. They are popular, and not just by emacs -- for example, window managers often use Ctrl-Alt-<arrow-key> for switching between virtual desktops. So, it's good to think a little bit where to 'spend' your easiest key bindings.

2008-12-23

quickly switching between header and implementation

A trivial yet useful trick: when coding C/C++, you often jump from header file (.h, .hh etc.) to implementation file (.c, .cc etc.). Emacs has built-in support for this, using ff-find-other-file. We can add a key binding to .emacs:
(add-hook 'c-mode-common-hook
  (lambda() 
    (local-set-key  (kbd "C-c o") 'ff-find-other-file)))
Now, we can quickly switch between myfile.cc and myfile.h with C-c o. Note the use of the c-mode-common-hook, so it will work for both C and C++.

2008-12-17

auto-detecting indentation style

When writing some C/C++-code, I usually follow a variant of the Linux coding style. Emacs understands this, if you put something like
(add-hook 'c-mode-common-hook
          (lambda ()
            (c-set-style "linux")))
in your .emacs. In practice, this means that e.g. pressing the Tab-key will do the right thing (there is a lot more to be said about that; but not here, not now).

However, sometimes I also need to edit other people's files, and they may use quite different settings - i.e., maybe they use spaces instead of tabs, or have the indentation set to 2(!). I may not like those settings, but I still want to respect them. If I would edit those files using my normal settings, I will likely screw up the existing code. It'd be nice if emacs would understand the existing settings, and use those instead of my own. Of course that is possible -- there are different ways to do that.

file local variables

First, the original author can explictly set the coding standard, i.e., if he or she puts something like
/* -*-mode:c; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
in the first line of the file, and Emacs will use those settings. See Specifying File Variables in the Emacs Manual for details. File-local variables can be useful sometimes, but they are not a very complete solution. They require original to actually add them, and changes are they don't; especially if they're not using emacs.

dtrt-indent

What I'd like instead is some way to auto-detect the settings for a file, and use those. And that is exactly what Julian Scheid's dtrt-indent does; add the following to your .emacs (if unclear, see the entries on hooks and external packages):
(add-hook 'c-mode-common-hook 
  (lambda()
    (require 'dtrt-indent)
    (dtrt-indent-mode t)))
With this, emacs will automatically update the indentation settings whenever you open a C/C++/Java/...-file. Some notes:
  • In addition to C-alike languages, dtrt-indent also supports shell, Ruby, and Perl, so you could add a hook to sh-mode, ruby-mode and perl-mode/cperl-mode as well;
  • dtrt-indent wisely lets itself be overridden by abovementioned file local variables, and will not change settings if it cannot determine the settings of the current file with some degree of reliability;
  • dtrt-indent currently only detects the indentation-style, not the coding style, ie. it does not detect if you want to put the '{' on the same line as the 'if', or on the next one. In practice, this turns out not to be a big problem, although it would be nice-to-have.
Anyway, a quite useful package, that I've been happily using for a while.

2008-12-14

showing trailing whitespace

When writing Makefiles, it's easy to accidentaly have some trailing spaces. This can then lead problems with lines ending in "\", for example:
  SOURCES = foo.c \
            bar.c
will ignore 'bar.c' if there is a space right of the '\'. I've bitten by this a couple of times, and it's not always directly clear that the reason for some linker errors is a superfluous space in the Makefile.

Some other editor makes those spaces/tabs visible; but by default emacs doesn't. However, it's easy to add a Makefile-hook to your .emacs:

(add-hook 'makefile-mode-hook 
  (lambda()
    (setq show-trailing-whitespace t)))
This sets the buffer-local variable show-trailing-whitespace, only for Makefiles (including Makefile.am and Makefile.in), and makes those trailing spaces visible.

Some people turn it on for all buffers, but I personally find that quite annoying: usually trailing whitespace does not mean anything.

Note that if you want to see all whitespace/tabs etc., you can use whitespace-mode (in recent emacs versions, use M-x whitespace) - which can be useful at times.

2008-12-11

highlighting lines that are too long

When writing code, I don't like my lines to be too long; the Linux Coding Style famously asserts that:
The limit on the length of lines is 80 columns and this is a hard limit.
In this case (and many others), I can heartily agree with this coding style. Longer lines are hard to understand (I use a limit of 100 for C++/Java).

As a small variation on the trick for highlighting "TODO", "FIXME" and friends, we can also highlight lines that are too long:

(add-hook 'c-mode-hook
  (lambda ()
    (font-lock-add-keywords nil
      '(("^[^\n]\\{80\\}\\(.*\\)$" 1 font-lock-warning-face t)))))

2008-12-10

highlighting "TODO", "FIXME" and friends

When doing some programming with emacs, I like to highlight certain words that are not language keywords, but still have some special significance to me.

The emacs manual mentions this really useful trick:

(add-hook 'c-mode-common-hook
               (lambda ()
                (font-lock-add-keywords nil
                 '(("\\<\\(FIXME\\|TODO\\|BUG\\):" 1 font-lock-warning-face t)))))
This adds a hook function, a function that will be called when we open a C-file, so whenever there is a 'FIXME:', it gets a different color, so it stands out:
/* FIXME: check for foo */
Some notes:
  • I am using c-mode-common-hook instead of the c-mode-hook (as the emacs manual does); this means that this will work for all C-mode languages - C/C++/Java/Objective-C/...
  • I also added some extra keywords (TODO, BUG); you can of course add your own keywords there as well. It might help to use M-x re-builder (the Emacs regular expression builder), as Emacs regular expressions can be quite tricky to get right...