Save Visited Files, V1.1

October 22nd, 2009

If you remember a post I wrote a while back, I had made a mode save-visited-files that was a lightweight replacement for desktop.el.  It saves the files you have opened, reloading these whenever you start emacs.  Ryan Thompson spent some time improving save-visited-files, so I thought I’d release his improvements.  save-visited-files.el can be downloaded from here.

Save-visited-files now uses auto-save-hook instead of a periodic timer.  This is probably the better decision, but it means you don’t want it to trigger too often.  In order to reduce the number of auto-saves, you can use the following, which will auto-save every 3000 input events:

(setq auto-save-interval 3000)

The functions and variables in save-visited-files are also named more consistently, with each one being prefixed with save-visited-files.  The mode can now also be customized with M-x customize-group save-visited files.  As a final improvement, the handling of the temporary buffer is handled much more nicely, so that the user is never presented with it.

To use the new save-visited-files, just put the following in your .emacs file:

(require 'save-visited-files)
(turn-on-save-visited-files-mode)

More Gmail with Emacs

October 21st, 2009

The last time I talked about using Gmail from Emacs, several people suggested using Wanderlust, an IMAP client written in ELisp. Details for setting it up can be found here; just following those set it up well for reading my email. This worked until I wanted to send a mail from emacs, and found that wanderlust had replaced emac’s send-mail function with it’s own, which didn’t work. I tried for a bit to figure out why it was failing, but eventually gave up on wanderlust and set GNUs up for gmail again.

After this, I decided to try using GNUs for accessing my Gmail again. This process is fairly easy:
put the following in your configuration file:

(setq gnus-select-method '(nnimap "gmail"
(nnimap-address "imap.gmail.com")
(nnimap-server-port 993)
(nnimap-stream ssl)))

Once you have evaluated this expression, do M-x gnus and then S s and enter INBOX. This will switch to your GMail inbox. There are a few problems with this, however. The first is that very few messages are actually presented to you; even though it asked how many to retrieve, and I used a value of ‘100′, only three were presented. I really want to be able to read older mail; If anyone knows how to fix this, please let me know. The other issue, which isn’t as bad, is that read mail does not update the Gmail web interface as read.

Getting back to sending emails, I wrote a function to allow me to easily insert emails. It works for both individual people and multiple addresses.

(defun insert-email ()
(interactive)
(insert (cadr (assoc (ido-completing-read
"Name: "
(mapcar #'car email-alist))
email-alist))))
(global-set-key (kbd "C-c m") 'insert-email)

This function uses the value of email-alist, which is an alist of names to emails. This doesn’t even have to be used to insert emails; that’s just what I’m using them for. To set email-alist to the proper value, use:

(setq email-alist
'(("Name1" "email1")
("Name2" "email2")))

This ends up letting you use Ido to select between name1 and name2 to insert email1 or email2. As I said, it’s more general than what I’m using it for currently - you can use it select any arbitrary text for insertion.

C++ Customizations for Emacs

October 19th, 2009

I’ve been doing more C++ than usual for courses, so I ended up revisiting my C++ configuration and loading up some old customizations that I had in order to be more productive. I didn’t pull in all of my old ones, such as all the CEDET stuff that had been slowing down my emacs significantly, but I did find some useful customizations that I had and wanted to put back in.

The first was to define a project type for C/C++ projects using eproject. This lets you easily switch between files in the same project, as well as perform other actions described in the linked post. I define the project base to just be the topmost directory with a Makefile.

(define-project-type cpp (generic)
  (look-for "Makefile")
  : relevant-files ("\\.cpp" "\\.c" "\\.hpp" "\\.h"))

Another re-addition is member-function.el, a mode that will automatically expand member functions in class definitions with stubs. This ends up saving me a lot of time, since I don’t have to write out the function definitions twice for every function - I just add it to the class definition and then it appears in the corresponding implementation file.

Normally expand-member-function must be run interactively and prompt you for the header and implementation file, but I just created a function that would find these values and run it with the correct values. I added it to c-mode-hook, which will cause it to be run whenever a C/C++ file is opened, without me having to do anything.

I also got tired of typing in #ifndef blocks for my header files, so I wrote a function that would insert this in newly-created .h and .hpp files. I also added this function to c-mode-hook, making it so I never have to type one again (I hope).

(defun h-file-create ()
  "Create a new h file.  Insert a infdef/define/endif block"
  (interactive)
  (if (or (equal (substring (buffer-name (current-buffer)) -2 ) ".h")
          (equal (substring (buffer-name (current-buffer)) -4 ) ".hpp"))
      (if (equal "" (buffer-string))
          (insert "#ifndef "(upcase (substring (buffer-name (current-buffer)) 0 -2)) "_H\n#define "
                  (upcase (substring (buffer-name (current-buffer)) 0 -2)) "_H\n\n#endif"))))
 
(defun c-file-enter ()
  "Expands all member functions in the corresponding .h file"
  (interactive)
  (let ((c-file (buffer-name))
        (h-file (concat (substring (buffer-name (current-buffer)) 0 -3 ) "h")))
    (if (equal (substring (buffer-name (current-buffer)) -4 ) ".cpp")
        (if (file-exists-p h-file)
              (expand-member-functions h-file c-file)))))

I also occasionally write small C++ programs for testing purposes. In these cases, it’s nice to be able to do a M-x compile and have it work without having to manually type in a compile-command. yourself. This will set the compile-command to one that will appropriately compile the current file if no Makefile exists whenever a c/c++ file is opened.

(add-hook 'c-mode-hook
          (lambda ()
            (unless (file-exists-p "Makefile")
              (set (make-local-variable 'compile-command)
                   (let ((file (file-name-nondirectory buffer-file-name)))
                     (format "%s -c -o %s.o %s %s %s"
                             (or (getenv "CC") "g++")
                             (file-name-sans-extension file)
                             (or (getenv "CPPFLAGS") "-DDEBUG=9")
                             (or (getenv "CFLAGS") "-ansi -pedantic -Wall -g")
                             file))))))

I also finally learned how to properly use tags. Tags allow you to quickly navigate to declarations of functions and symbols in your program. To use tags, you must first create a tags file using either etags or exuberant ctags - etags comes with emacs, so you will have at least one of these. You use one of these to generate a TAGS file just by using ‘etags’ in the directory you wish to create a TAGS file in. It will automatically scan all files and subdirectories to create this file.

Once your index is created, you can jump to the definition of a function with M-.. This will prompt for a TAGS file the first time you use it, and then use that index to jump to the function definition you supply (defaulting to the one at point). If there are several conflicting definitions, C-u M-. will go to the next possible definition. Once you are done with that location, M-* will take you back to where you originally jumped from. C-x 4 . will perform a find-tag, but will open the declaration in another window. There are a few other tags commands, but these are the most useful ones. To find out more, read the TAGS node in the Emacs manual.

One last utility I added was . Cscope is the reverse of etags; given a symbol, it will find all uses of that symbol. To use it, cscope must be installed; in Ubuntu you can do this with ’sudo apt-get install cscope’. To use it, just use M-x cscope-find-c-symbol to have it output a list of all references to the symbol; this list is linked to your source, so you can jump to files by pressing ‘enter’ on the line you have selected. cscope-find-functions-calling is also useful; it iwll return a list of all functions that call the function you specify. There are a few more commands, but these are the ones I use; look at the commands starting with cscope- to find a list of them. To enable cscope, you need to put cscope.el in your load path and add the following to your initialization:

(require 'cscope)

Bitlbee and Emacs

October 16th, 2009

As part of switching to bitlbee as my primary IM client, I ended up making a lot of customizations to my erc configuration, both for general use and for bitlbee-specific stuff. I didn’t really have any beforehand, since I don’t use IRC very much, but these make it a lot more usable with bitlbee. Bitlbee can be pretty annoying at the start; these help to make it much less so. Most of the general ERC customizations came from the emacs-Viki, but most of the bitlbee-related code is mine.

The first customization I made was to set the header-line of disconnected buffers to be a different face than normal. The header line is just the top line of the buffer; some modes, such as ERC, use it for displaying information about the current context. This just makes it easier to tell which ERC buffers are still connected to the server.

(defface erc-header-line-disconnected
  '((t (:foreground "black" :background "indianred")))
  "Face to use when ERC has been disconnected.")
 
(defun erc-update-header-line-show-disconnected ()
  "Use a different face in the header-line when disconnected."
  (erc-with-server-buffer
    (cond ((erc-server-process-alive) 'erc-header-line)
          (t 'erc-header-line-disconnected))))
          (setq erc-header-line-face-method 'erc-update-header-line-show-disconnected)
 
(setq erc-header-line-face-method 'erc-update-header-line-show-disconnected)

I like to log my IM messages. I often have useful discussions with people, or receive information from them, that I want to refer to later. The following sets my log directory and updates them whenever the ERC buffer is updated, ensuring I never lose information.

(setq erc-log-channels-directory "~/.emacs.d/logs/")
(setq erc-save-buffer-on-part nil)
(setq erc-save-queries-on-quit nil
      erc-log-write-after-send t
      erc-log-write-after-insert t)

IRC in general will give a lot of messages that you don’t care about, and there are some bitlbee-specific ones as well. erc-hide-list is a list of types of messages that ERC will hide, and erc-ignore-unimportant is a function I wrote to suppress other information I don’t want to see. This includes mode changes for people and reconnection attempts when an account is already online.

(setq erc-hide-list '("MODE"))
(defun erc-ignore-unimportant (msg)
  (if (or (string-match "*** localhost has changed mode for &bitlbee to" msg)
          (string-match "Account already online" msg)
          (string-match "Unknown error while loading configuration" msg))
      (setq erc-insert-this nil)))
(add-hook 'erc-insert-pre-hook 'erc-ignore-unimportant)

Speaking of reconnection attempts when an account is online, I have ERC automatically connect me to my accounts whenever I log on as well as every 60 seconds. This simulates the behaviour of other IM clients, which will auto-reconnect when disconnected.

(defvar bitlbee-password "<SECRET>")
(defun bitlbee-identify ()
  "If we're on the bitlbee server, send the identify command to the
 &bitlbee channel."
  (when (and (string= "localhost" erc-session-server)
             (string= "&bitlbee" (buffer-name)))
    (erc-message "PRIVMSG" (format "%s identify %s"
                                   (erc-default-target)
                                   bitlbee-password))))
(add-hook 'erc-join-hook 'bitlbee-identify)
 
(defun bitlbee-connect ()
  (interactive)
  (save-window-excursion
    (when (get-buffer "&bitlbee")
      (switch-to-buffer "&bitlbee")
      (erc-message "PRIVMSG" (concat (erc-default-target) " identify " bitlbee-password))
      (erc-message "PRIVMSG" (concat (erc-default-target) " account on 0")
      (erc-message "PRIVMSG" (concat (erc-default-target) " account on 1"))))))
(setq bitlbee-reconnect-timer (run-with-timer 0 60 'bitlbee-connect))

The ‘blist’ command for bitlbee will list your buddies and their statuses. However, by it doesn’t do any color-coding for your Friends who are online vs who are away, so I had to add this. It isn’t very difficult; erc-keywords is a list of keyword-face pairs that the keyword is matched with. All you need to do to perform any type of highlighting is be able to match the message you want highlighted with a regular expression.

(setq erc-keywords '((".*Online.*" (:foreground "green"))
                     (".*Busy" (:foreground "red"))
                     (".*Away" (:foreground "red"))
                     (".*Idle" (:foreground "orange"))
                     ))

One of the reasons I switched from Pidgin to Bitlbee was that Pidgin was no longer notifying me of new messages; I decided to try seeing if I could implement this for bitlbee. It actually turned out to be pretty easy, although there is one problem: it only occurs for messages sent to the public channel, not private messages, so it won’t inform me when someone starts a conversation with me. I’m still looking into how to fix this.

(defun erc-notify-on-msg (msg)
  (if (string-match "nflath:" msg)
      (shell-command (concat "notify-send \"" msg "\""))))
(add-hook 'erc-insert-pre-hook 'erc-notify-on-msg)

The last customization I have to bitlbee is so that I don’t have to type the user I’m addressing each time in the public channel. Usually, you have to prepend each message with user: in order for it to be sent to them; this code will auto-prepend messages with the last user you addressed. It’s a work in progress, as a lot of cases I don’t want this to happen - for example, when I’m listing my buddies - but it’s pretty good right now.

(setq bitlbee-target "")
(defun bitlbee-update-target (msg)
  (if (string-match "\\([^:]*: \\)" msg)
      (setq bitlbee-target (match-string 1 msg))
    (if (not (or
              (string-match "account" msg)
              (string-match "help" msg)
              (string-match "identify" msg)
              (string-match "blist" msg)))
        (setq str (concat bitlbee-target msg)))))
(add-hook 'erc-send-pre-hook 'bitlbee-update-target)

I generally want to be logged into IM, so I just start it up on emacs start.

(erc :server "localhost" :port "6667" :nick "nflath" :password bitlbee-password)

If you have any other customizations or improvements to suggest, please let me know in the comments.

Emacs Settings

October 14th, 2009

I recently upgraded to 23.1.5 from 23.0.6, and a few of my customizations broke - not many, but I also made a number of changes to my configuration, so I figured I’d cover them all here. Overall, it was a pretty easy process - the only customization that broke that I still haven’t figured out is Slime breaking. It works if I run everything up to and including the call to slime, but not if I then continue running my other customizations.

These first customizations modify general Emacs behavior. debug-on-error will give a backtrace when an error is encountered in any running elisp code; this makes it much easier to debug problems. If display-battery-mode is on, your battery level and heat is shown in the mode line. apropos-do-all will make apropos do everything; it is much more useful this way. Setting pop-up-windows to nil will stop emacs from changing your window configuration, and confirm-nonexistent-file-or-buffer will stop emacs from prompting you whenever you create a new file.

(setq debug-on-error t)
(display-battery-mode t)
(setq apropos-do-all t)
(setq pop-up-windows nil)
(setq temporary-file-directory "~/.emacs.d/tmp/")
(setq confirm-nonexistent-file-or-buffer nil)

I also noticed that hitting the spacebar now inserted a space character in my minibuffer. This is essentially never what I want, so I changed it to completion with:

(define-key minibuffer-local-map (kbd "SPC") 'minibuffer-complete)

The next set of customizations I added modified the behaviour of shell modes. The first one will cause cycling to skip unique values; if you run the same command twice, M-p twice will take you to a different commands. The other two are fairly self-explanatory, and are for showing as much as possible in the buffer.

(setq comint-input-ignoredups t)
(setq comint-scroll-show-maxiumum-output)
(setq comint-scroll-to-bottom-on-input t)

Finally, I added a few functions to help out. M-x google will now prompt me for a search string and then open a browser with a query for that string. Line-matches is used programatically in order to tell if the line point is on matches the given regular expression.

(defun google (query)
  "googles a query"
  (interactive "sQuery:")
  (browse-url (concat "http://www.google.com/search?q=" query)))
 
(defun line-matches (regexp)
  "Returns non-nil if the current line matches the given regexp, nil otherwise."
  (save-excursion
    (end-of-line)
    (let ((end (point)))
      (beginning-of-line)
      (re-search-forward regexp end t))))

Docview

October 12th, 2009

docview is a built-in document viewer for Emacs that can display dvi, ps, and pdf files. It isn’t as good as most PDF readers, but in a lot of cases it’s good enough without having to switch to a different application. It works by converting the files to a series of ‘png’ images, one per page, which Emacs can display. This means that you can’t edit them or copy text from PDF files, but if you only need to view them it works.

docview is enabled by default in emacs - opening a pdf file as a normal file will turn on docview-mode. The only customization I currently have for it is to turn on auto-revert for pdf files; I use this when creating a PDF file using latex and wish it to be auto-updated. There’s not much else I can think of that would improve this mode by the use of hooks - mostly to make it better Emacs would need native PDF support.

(add-hook 'doc-view-mode-hook 'turn-on-auto-revert-mode)

Using docview is fairly simple: n/p will move to the next or previous page and C-n/C-p moves up or down on the current page. You can zomm in and out with + and - respectively. Other normal movement keys are rebound to something appropriate - M-> will go to the last page, for example. You can also search for text with ‘C-s’ and ‘C-r’, but this will only take you to the correct page and message you the line the text is on - it won’t highlight the text for you, so it is rather subpar.

Gmail from Emacs

October 9th, 2009

I’ve meant to set up email from emacs for a while, but only recently got around to setting it up. I use GMail, so I’d wanted email sent from emacs to appear as being sent from my gmail account. To do this, you must install the ’starttls’ program. On Ubuntu, this can be done with ’sudo apt-get install starttls’. Once that is done, put the following in your .emacs file:

(setq send-mail-function 'smtpmail-send-it
      message-send-mail-function 'smtpmail-send-it
      smtpmail-starttls-credentials
      '(("smtp.gmail.com" 587 nil nil))
      smtpmail-auth-credentials
      (expand-file-name "~/.authinfo")
      smtpmail-default-smtp-server "smtp.gmail.com"
      smtpmail-smtp-server "smtp.gmail.com"
      smtpmail-smtp-service 587
      smtpmail-debug-info t)
(require 'smtpmail)

You will also need to create a ~/.authoinfo file with the following format:

machine smtp.gmail.com login username@gmail.com password secret

Once you add these customizations, you will be able to use ‘C-x m’ in order to create an email and send it to people. However, this does not allow you to read and reply to email from emacs. Unfortunately, I haven’t found a great solution for that yet; I tried using GNUs a while ago and didn’t like it, but if you want to try it the information on how to do so is located on the emacs-wiki. The other option that I sometimes use is to have a w3m buffer open and pointing to Gmail, but w3m isn’t as good as I would like and so this isn’t the best experience either. Let me Please let me now if you know of a better way to handle mail from emacs.

Guava: Google Libraries for Java

October 7th, 2009

Guava is a set of Java Libraries recently provided by Google. The API reference for it is located here, but I’ll provide a very, very brief overview of some of the classes provided. These libraries aren’t at a release version yet, but they still seem quite usable.

CharMatcher - An instance of CharMatcher represents a set of matching characters. You can use predefined constanc CharMatchers, such as CharMatcher.WHITESPACE or CharMatcher.WHITESPACE, or you can also use a factory method, such as CharMatcher.oneOf(”ABC”). Alternatively, you could subclass CharMatcher and implement matches(char c). Operations on a CharMatcher represent what you want done for characters that are matched by the CharMatcher for a string. Some of these are matchesAllOf, removeFrom, and retainFrom. For more examples, see the Guava API documentation.

Charsets - predefined constants for charsets supported on all JVMs (for example, UTF-8) which do not need UnsupportedEncodingExceptions.

Joiner - this class joins pieces of text with a separator. Works on arrays, Lists, and Maps. This

Splitter - Much better than String.split, constructing on and using the split( String s ) method will return an iterator over the pieces of the string. It can be configured for how you want to handle empty pieces, unlike the String.split method. You can also split on strings that are not regular expressions, and are not required to have an array.

Guava also has a set of classes for utilities on primitive objects. They give primitives hashCode, compare, and many other methods for primitives. They also provide an asList method that allows viewing an array as a List. Another feature is utilities for dealing with both signed and unsigned bytes. For more of the details, check out either the API documentation or the introductory PDF.

Guava also provides a set of classes for dealing with IO. There are utility methods for Streams, Files, and other IO classes. One of the notable standouts here is the Files.readLines method(). There are two methods with this name: one takes a File and a CharSet and returns a List containing the file. The other method also takes a LineProcessor class, which is an interface containing processLine(String) and getResult(). Each line will be called with processLine(String), and the once all the lines have been processed the result of getResult() will be returned.

Guava also provides a set of utilities for concurrency. I haven’t done very much with concurrency, so I can’t really talk about these much. I’d suggest looking them over yourself and seeing if there’s anything you can use. I’ll definitely come back and check out what they have when I have some program that needs to have concurrent threads.

Practical Virtual Method Call Resolution for Java

October 5th, 2009

This paper was on new methods of statically determining which methods can be called by virtual method calls in Java. This is used for method inlining and producing more accurate call graphs, which can improve other analysis. This paper suggest two algorithms that builds type propagation graphs, where vertexes are variables and edges represent the flow of types due to assignments,. anc compares them against CHA and RTA. These new algorithms were designed so that they would scale linearly with the size of the Java program being analyzed. The analysis was implemented with the Soot framework, which provides Jimple, which is a representation of Java bytecode. Thus, this analysis can be used for all JVM languages and not just Java.

The Soot framework is an APO for manipulating Java bytecode. The implementation of the algorithms worked by reading all class files required by an application, converting them into Soot representations of the class, with Jimple classes representing the bytecode. Once the analysis and transformation is complete, the optimized code is output again as bytecode.

Class Hierarchy Analysis is a method for determining the set of types for objects used in Java applications. Basically, for any method call c.m() where the declared type of c is a class, the possible types of c are the declared type of c and it’s subclasses. If the declared type of c is an interface I, the possible types of c are all classes that implement I or a subinterface of I, plus all classes that are subclasses of those classes.

A call graph consists of one node for each method that is reachable from the main method. Each node in the call graph contains a collection of call sites, which are method calls. Edges go from call sites to all nodes that could be called from that call site. This call graph may contain edges and nodes that are not necessary; we want to remove these as much as possible.

Rapid type analysis is a way to improve the call graph. It uses the fact that an object can only be called if it is created by a ‘new’. There are two types of RTA: optimistic and conservative. In conservative RTA, CHA is performed and then the reachable methods are inspected to determine which types can be instantiated. Optimistic RTA constructs the call graph iteratively,

The two new algorithms refine RTA using the property that for any call c.m(), c can only be a type T if there is an expression of the form v = new T() followed by a set of assignments x_1 = v, x_2 = x_1, …, x_n = x_{n - 1}, c = x_{n - 1}. The two analysis work by building a type propagation graph, where nodes represent variables and a directed edge from a to b represents an assignment of the form b = a. This graph is used to determine which variables that methods are called can correspond to which classes in a more precise way than RTA.

One of the new algorithms, Variable-Type Analysis, uses the name of a variable as its representative. There are three types of variables, with the following representative names: local variables/parameters have a name C.m.a, fields are named C.f, and array references are named a[x].

The nodes of the type propagation graph is constructed as follows:

For every class C in the program:
    For every field F in C
        create a node C.F

For every method C.m in the call graph of P:
    For every parameter p_i of C.m, create C.m.p_i
    For every local variable l of C.m, create C.m.l
    Create C.m.this
    Create C.m.return

Afterwards, assignments between variables in the form of assignment statements and method calls are used to construct the edges of the type propagation graph. Native methods have their information input by hand. Aliases do not affect this alias’, because locals and fields cannot be aliased - if there is are two locals a and b, they refer to different locations. This is not true for arrays, and references to arrays can be stored in Objects. To solve this issue, when adding edges to the type propagation graph, if the two types are of array types or java.lang.Object, a bidirectional edge is added to the graph. Declared-type analysis works the same way, except that a node is used for each declared type and not each variable. The size of the graph is smaller, since there are fewer nodes, but the final answer is less precise.

To keep the algorithm simple, some design tradeoffs were made:

  • Aliases - To avoid solving the aliasing problem except in the case of arrays, one node was used for all instances of a field instead of one per arrays.
  • No killing based on casts - For assignments of the form lhs = (C)rhs, we do not take into account the extra type information given by the task of C, as this would require either a iterative solver or a more complex constraint solver.
  • Pessimistic algorithm - The algorithm adds edges for all method calls in the conservative call graph, instead of using which types could currently reach the call at each step of the analysis. However, this would require iteration. We improve the pessimistic algorithm by generating a better conservative call graph.
  • A whole-program approach - Instead of only propagating type information within a procedure and using the call graph to determine the effect of method calls.
  • A 3-address representation of bytecode - This greatly simplified the analysis

Seven benchmarks were used to compare algorithms, including javac. One use of these algorithms is to reduce the size of the call graph. For this, both VTA and DTA perform better than even optimistic RTA, with VTA performing better. VTA removes 10% to 65% of the methods and 17 to 65% of the edges, whereas optimistic RTA varies from 7% to 56%. VTA has more notable improvements on more object-oriented benchmarks. VTA in general seems to be an improvement over RTA in all cases.

The other measurement is how many polymorphic calls. Given a call graph constructed by CHA, the percentage of polymorphic calls that were determined to be monomorphic by RTA, DTA, and VTA were measured. VTA showed a significant improvement, whereas RTA and DTA did not prune the call graph very much - VTA can resolve between 12% and 96% of the calls. The benchmarks were then instrumented to output profiling information to construct a complete call graph. On the large OO benchmarks, while VTA did significantly better than RTA, it still did not match the profiling information. In javac, VTA only determined 82% of the calls that the profile indicated were monomorphic. There are two ways to attempt to improve this percentage; perform more expensive static analysis or do dynamic optimization, such as branch target prediction.

Using this information to implement inlining showed small increases in speed on both the soot and javac benchmarks. For soot, using CHA to determine monomorhpic calls gives a 1% speedup in execution time, whereas VTA give 3% speedup. In javac, these percentages are 0% and 2%.

Both DTA and VTA behave linearly in practise, and thus scale well. VTA is approximately a constant factor of 10 slower than DTA, and so while is more precise is also more expensive. In conclusion, VTA gives significant improvements to DTA, which performs better than both CHA and RTA.

Bitlbee

October 2nd, 2009

I usually use pidgin for my instant messaging, but recently it has stopped alerting me when I get messages. I wasn’t entirely sure why, but it meant I kept missing messages from people and was incredibly annoying. A combination of this and the fact that I wished to be able to stick in Emacs for chatting sent me out on a search for a new messaging program.

Emacs itself has a few packages that claim to do instant messaging support, bust most are either in early stages, flat-out don’t work, or don’t support the protocols I need. TNT, for example, works quite well - but only for AIM. Since in most cases I use either MSN or Gmail, that strikes TNT out. Unfortunately, it seemed I was going to have to either switch to another external IM client or just keep using Pidgin. Then a friend of mine told me about Bitlbee.

Bitlbee is a program that will create an IRC server that you can use to communicate via MSN, Jabber, and a few other protocols. You can use it to MSN via a terminal running IRSSI; I decided to use ERC, Emacs’ built-in IRC client. The bitlbee we page is located here; go there if you need to report a bug, or want more information than is provided in this post.

Installing Bitlbee is easy, if you are on Ubuntu. A simple ’sudo apt-get install bitlbee’ will install it. I’m not entirely sure how to do it on other operating systems, but the source is provided so in the worst case scenario you can just build it yourself. Once this is done, the command ’sudo /etc/init.d/bitlbee start’ will start the IRC server. Connect to this on localhost:6667 and you are ready to go.

Once you join the IRC server, you will need to register your account. Do this by sending the message ‘register pass’, where pass is your desired password. After this, you can start adding accounts. Adding a MSN account is done by ‘account add msn username@userdomain pass’. Gmail accounts require two commands to add: The first is ‘account add jabber user@gmail.com pass’ and the second is ‘account set 1/server talk.google.com’ The 1 in the previous command may differ in your case: find which number you should be using by sending ‘account list’. Connecting to your accounts is done with ‘account on #’. Once you are logged in, you probably want to save your configuration with ’save’.

Once you have connected to your accounts, you can see all your buddies and their statuses with ‘blist’. Messaging them can be done in two ways, the first of which is to prefix the message to them with ‘username: ‘. In this case, replies they send to you will appear in this main channel. If you want a private message to be opened, you can message them using the standard ‘/msg user’ command. This is probably what most users will want; I haven’t used bitlbee with ERC enough to know which I prefer.

Of course, you will probably want to add new contacts eventually. This is done with the ‘add’ command. To use it, just ‘add # user’, where # is the number of the connection you want to add the user to and user is their username. The other command you’ll want to know aobut at the start is ‘rename’, which will allow you to alias users with ‘rename user alias’. Since many people have usernames that don’t make it obvious who they are, this command is pretty much required for a chat application.

That is everything I needed to do to get set up with Bitlbee and start chatting. To access its help system, use ‘help’ in the bitlbee server. There are a few other things I want to investigate that aren’t a huge priority for me: the ability to merge users and to export my aliases are two of them. It doesn’t look like there is a way to export data from bitlbee, although there is a bug report filed. The ability to merge users is probably not possible in bitlbee itself, but it’s not a big deal and I can probably just code something in elisp to handle that case.