Archive for the ‘Lisp’ Category

In case you thought Lisp was dead …

Wednesday, March 5th, 2008

Two days ago I went to the largest usergroup meeting of any kind I have ever seen. It was the Boston Lisp Meeting (although it should be called the Cambridge Lisp Meeting, IMO). There were about 40 people in attendance, and when I left (at 22:00, four hours after my arrival), it still rivaled any usergroup in size.

With 40 people, the sitting-around-a-table-drinking-beer format is perhaps not the most effective. Sure, there is plenty of conversation to be a part of, but any single participant necessarily misses the majority of what\’s going on. So, I apologize at the beginning that this can not be a comprehensive report, but rather an experiential summary of what I observed that fateful evening.

I showed up at 18:00, with probably over twenty people bulging from a single long table. Almost everyone who came after me ended up filling a second table. I took note of a few big names right off the bat (from #lisp and elsewhere): Rahul Jain (who traveled from New York) had come with me, and certainly Faré (our great organizer) was already there. Jeremy Jones (a founder of Clozure) and James Knight (foom) were also there before me. Alistair Bridgewater (aka, nyef) trekked down from New Hampshire, but I think Hans Hübner won the longest-distance award, having come all the way from Berlin. Ok, this list is getting crazy … there were also other well-known lispers in attendance. Gary King was supposed to have been there, but I didn\’t see (or perhaps recognize) him. Both Zach Beane and dto had to miss because of transportation issues, which was quite disappointing.

I was afraid the group would be dominated by ITA employees, but I think they made up maybe a quarter of the entire group. None of the guys near me at the beginning were ITA employees, in fact, I think they were all Lisp hobbyists. As a result, there is always plenty of discussion about how to go about making Lisp your profession, which is a topic I do like to talk about. One of my favorite questions was \”If you get to write Lisp at work all day, do you work in other languages when you get home?\” The answer is pretty much \”no\” … at least, I don\’t play with other languages any more than I did before I was writing Lisp professionally.

Later on in the night I moved around the table to see what was happening at Faré\’s end. There seemed to be a lot of discussion about when meetings should be held, and how to organize them, etc., which is great to hear. We\’ll be moving to a more presentation-oriented format, and I\’m sure Faré will have all the details about future meetings sent around soon. There was an XO laptop that got passed around so everyone could enter in their contact information and how they would like to be involved with future mettings. So there ended up being a bit of discussion about the XOs, and who managed to get one (like me) and who didn\’t.

Toward the end of the night, I got around the table to talk with Rahul and another of my co-workers, and had the chance to finally meet Alistair. Unfortunately, I had to leave shortly after we began talking … and he will be farther away than NH for the next few months because of various contracts he\’s working on. Hopefully he\’ll come to meetings when he\’s back in the region.

I know … there\’s not much Lisp content in this post. Honestly, it\’s hard to remember exactly what was discussed. The meeting was great for getting to know more Lispers, and there was plenty of Lisp talk, but my focus at the time was more on having a good time (and some beers) with people that I have a lot in common with. There will be plenty of in-depth Lisp-hackery at future presentation-based meetings. For now I\’m just excited about there being so many people here who are interested in it.

Continuing about restarts

Tuesday, February 26th, 2008

Update: these changes (along with an additional one for unbound slots) are now available in the CCL repo:<os><arch>/ccl

When I read Geoff Wozniak’s post (I know, I\’m a week behind) I was disappointed to see Clozure CL wasn’t even taken into account. I decided to check it out for myself. Initially, I was a bit disappointed, but after only a couple minutes of hacking, I managed to improve the situation a bit.

Situation Lisp implementations
Allegro CL Lispworks SBCL CLISP Clozure CL
No function defined -
Failed function lookup - - -
No class found - -
Division by zero - - - -
No method found -
No slot found - - -
Replace function with generic function -
Redefine a generic function - - 1

1 The existing code handled a defmethod followed by a defmethod with an incompatible lambda-list, but not a defmethod followed by a defgeneric with an incompatible lambda-list.

Initially (the black) we could claim superiority only to SBCL [Ed: just kidding, guys], but after my changes (in red) we’re now on par with Allegro. And Open Source. The squeaky wheel and all that. Thanks to Geoff for pointing out the issue.

Note: these changes currently exist only on my own box. I\’ll get them into CCL 1.2, though.

Boston Lisp Meeting

Monday, February 25th, 2008

It\’s been about four months since I last posted, which is really unacceptable. I feel like I have to jump on the bandwagon with this announcement, though, and maybe it\’ll get me back on track.

Next Monday (3 March 2008), is the inaugural Boston Lisp Meeting. Judging by talk around the office and in the community at large, it sounds like it\’ll be well-attended. If you know any lispers, send them along. If you want to get to know some, come along yourself.

automated testing with CL & darcs

Sunday, October 21st, 2007

I spent a good chunk of today trying to get darcs to run my unit tests automatically. I haven\’t actually gotten it right yet, but at least I have it running the tests before each commit (even if the commit happens regardless).

I set up the auto-testing with darcs setpref test \"chmod +x test/run-tests; test/run-tests\". test/run-tests is the test script, but darcs doesn\’t allow you to add executable files to the repository, so you have to run chmod on the script before it can actually be executed.

Here\’s the test script itself:

sh: /home/pfeilgm/bin/enscript: No such file or directory

What it should be doing is running the tests, and returning non-zero on failure. It runs the tests, but the failure bit isn\’t exactly happening yet.

I figured I\’d throw this out there and see if anyone else has a decent way of getting automated testing happening. The more I try to bridge between Lisp and Unix, the more I just want to live in a Lisp REPL.

Releases 1.1.0

Thursday, November 16th, 2006

Yesterday\’s post was perhaps a bit off the cuff. There were a lot of people really scared about my script, and I don\’t blame them. A lot of good points were brought up. It\’s not that I didn\’t consider them, it\’s just that they\’re already taken into account with how I do revision control. At least Luis had faith in me :)

Below is an example of how I tend to organize a project (my pre-1.0 releases are a bit different, so I\’m just leaving them out for the moment). There are effectively two kinds of tags, fixed (in black) and mobile (in red).


Notice that all the fixed tags are three-number versions. This means that if you request my-library_1.1.1.tar.gz, you\’re going to get that same code point all the time. However, you probably don\’t want to do that …



Thursday, November 16th, 2006

Quick followup to my last post before I go to sleep. Here\’s a partial and buggy implementation for CVS and darcs. Yay. Maybe it\’ll get better tomorrow.

sh: /home/pfeilgm/bin/enscript: No such file or directory

Breathe in … and Release

Wednesday, November 15th, 2006

I wouldn\’t say I disagree with Jack Unrue\’s statement about releases being necessary, but I think there\’s a way to make both groups happy (and maybe I should just get around to implementing it). If the no-release crowd thinks that we don\’t need to indicate functionality changes in some way, there\’s still an impasse. If that\’s not the case, I may have a solution.

We all know that a URL doesn\’t have to point to a file, so what if created the archive on the fly? It would be built from the \”my-library\” repository, using the tip of the \”0.3.4? branch, using tar -cz (if the user had typed \”.tar.bz2\” on the end, it would have used tar -cj). You can, of course, cache the archive (just check to make sure there are no new commits since the last build).

What are the benefits of this? Well, the developers don\’t need to explicitly build release packages. Also, any bug fixes that get merged into the branch are included whenever the next person requests that archive. It gives the user the same interface that they\’re used to. It works fine with ASDF, etc. (as long as you remember to set the latest tag on your current branch).

Actually, this may work better as a commit hook than being pull-based. This should be pretty trivial to build for any specific source control system. Maybe it\’s my project for this evening.

Subsequent Thoughts on Concurrency

Tuesday, November 7th, 2006

Over the past few years my opinions on concurrency have changed. I mean, threads were always a pretty scary thing. I figured that no matter what I did, there must be a race condition or deadlock in there somewhere (and really, if you ever think otherwise, you\’re just fooling yourself). I didn\’t know of any alternatives. Java\’s approach seemed to have some merits — all you had to do was write synchronized, right? — and I took it a bit further with a language I was designing some years back. Here\’s an image from the spec:



Thursday, August 31st, 2006

So, I wrote a new HTTP client package for Common Lisp. I know, there are already a bunch, but they all seem to be pretty limited in their functionality (yes, even the one in Closure).

For one, they expect character content, which is fine when you\’re trying to load a Web page (as long as it\’s in the encoding the client expects) but not so much when you\’re dealing with binary data. There also isn\’t much support for \”Transfer-Encoding: chunked\”. Closure does that, I think, but no one else. I also have some other nice features:

So, I needed to handle both binary data and chunked encoding for what I\’m doing at work. I figured I might as well take some time to make a full implementation of RFC 2616. It\’s not quite perfect yet, so here\’s a list of the known shortcomings:

  • sometimes the content is returned as a byte vector, other times as a stream;
  • no parsing of date headers (I\’ll probably just steal this from Closure);
  • it might be nice to return a string in cases where we have a Content-Type (but this might just add confusion); and
  • handling other header fields.

None of these things prevents it from complying with RFC 2616, though (I think). So, it\’s just a matter of making it more user-friendly at this point. I\’d appreciate any feedback. There\’s just the darcs repository now, but I\’ll make this into a CLNet project if people are interested.

LispWorks Personal under SLIME on OS X

Sunday, May 21st, 2006

A while ago, Bill Clementson wrote about how to make Lispworks Personal Edition work under SLIME. It’s a lot harder than you might think (well, harder than I thought, anyway). And it seems like they change things over time to make it even more difficult. So, Bill’s 18-month-old instructions no longer work. I did a lot of cursing while trying to fix it. Here’s what I came up with. (Again, this is mostly Bill’s work, I just changed what was necessary to have it work with LispWorks 4.4.6.)


Lisp Packages are Domains

Sunday, May 7th, 2006

In C2:CommonLisp, or any language that uses C2:GenericFunction s instead of class encapsulation, the package actually defines a domain. By domain, I mean a vocabulary in which each word has only one meaning.

Since C2:CommonLisp only allows for a single function signature within each package, this meaning for the word must be well-defined.

Often, the same concepts appear in multiple domains. Sometimes they keep the same names and it’s easy to :use a package in order to extend that domain with your own. However, sometimes the concepts carry over, but the vocabulary doesn’t. Currently that means that for each word in the vocabulary, you need to do this:

sh: /home/pfeilgm/bin/enscript: No such file or directory

Of course, defalias is a popular utility to make this renaming easier, but it\’s not part of the standard. I wonder if this could be made even simpler with an idea stolen from Eiffel: feature renaming:

sh: /home/pfeilgm/bin/enscript: No such file or directory

This makes the domain translation explicit.

Thinking of packages as domains may help limit the naming conflicts that arise in C2:GenericFunction-based OO systems, since people often try to use the packages much like Java packages, rather than like Perlpackages (a much closer, albeit single-dispatch, analogue).

Testing Lisp

Friday, March 31st, 2006

Gary King wrote an article not so recently about how to set up ASDF test-ops. I basically stole it, but have changed it a bit to work more intuitively (IMO). He arrives at the following test system definition:

(defsystem moptilities-test
  :components ((:module "test"
                        :components ((:file "tests"))))
  :in-order-to ((test-op (load-op moptilities-test)))
  :perform (test-op :after (op c)
                    (describe (funcall (intern "RUN-TESTS" "LIFT")
                                       :suite (intern "TEST-MOPTILITIES"
  :depends-on (moptilities lift))

(defmethod operation-done-p ((o test-op)
                             (c (eql (find-system 'moptilities-test))))
  (values nil))

However, it seems to me that (asdf:oos 'asdf:test-op :moptilities-test) should be testing the tests, not Moptilities. I would much prefer to see (asdf:oos 'asdf:test-op :moptilities), and this is possible with a little rearrangement.

You still need a test system, but it should be pretty minimal:

(defsystem moptilities-test
  :components ((:module "test"
                        :components ((:file "tests"))))
  :depends-on (moptilities lift))

Then, the other pieces should be in the primary system:

(defsystem moptilities
  :components (...)
  :in-order-to ((test-op (load-op moptilities-test)))
  :perform (test-op :after (op c)
                    (describe (funcall (intern "RUN-TESTS" :lift)
                                       :suite (intern "TEST-MOPTILITIES"
  :depends-on (...))

Yeah, in addition to moving things to the primary system, I also changed a couple strings to keywords … just a personal preference. Also, OPERATION-DONE-P should operate on the MOPTILITIES system, rather than MOPTILITIES-TEST. Oh, and I changed the package name from TEST-MOPTILITIES to MOPTILITIES-TEST. I?like to keep packages as nouns and functions as verbs.

I’m always searching through Gary’s archives to find this, and then re-remembering my variations, so this puts it all in one place for me (and maybe others) in the future. Leave a comment if you have any suggestions.

What I\’m playing with at home

Thursday, March 16th, 2006

This is an email I sent out to a few friends, talking about what we\’re doing with our time, and I realized that it\’s exactly the sort of thing I should be posting.

There are a number of models of computation, the most famous being the Turing machine and the λ-calculus (which are equivalent, but λ-calculus is prettier). They\’re both pretty old, dating from the 40s and 50s respectively. Of course, they\’ve pretty well stood the test of time. Two of the more modern ones that have held my interest are the ρ-calculus and the π-calculus. Both of these encode the λ-calculus very easily (meaning anything you can do with λ-calculus you can do with them).


Multiple Paradigms

Wednesday, March 8th, 2006

I\’ve got a few things floating around in my brain, making some odd connections. I recently watched Richard Dawkins\’ The Root of All Evil? where he discusses many of the problems with religion. And today I had a discussion with someone at work who didn\’t see why I would do a project in Lisp. We discussed a few different reasons, but there\’s one in particular I want to focus on, and I think it ties in with \”the religion problem\”.


The Language Game

Friday, February 24th, 2006

Those of you who know me well, may know of my aborted attempt at language design. While working on it, I hit what I call the \”language design singularity\” — a point at which you realize you\’re headed down the wrong path, and make that jump to the right one. I imagine a lot of would-be language designers hit the singularity. People get interested in design because they recognize the problems with the current system, and seek to improve the situation. At this point, their path begins to move closer to the singularity, eventually there is a jump, like when a metal rod slides close enough to a magnet, and you find yourself in a world where your problems don\’t exist.

For me, it happened like this … (more…)

Common Libraries for Common Lisp

Monday, December 12th, 2005

A frequent complaint about Common Lisp is that it doesn\’t have the sort of standard library that is so popular these days. Java, Python, Ruby … everything has a standard library now. When Common Lisp was standardized, its functions comprised an enviable library. But, times change, everyone else catches up, and you gotta keep on your toes to stay in the game. So what does CL need to do to get back in it? Not too much. There are a lot of libraries out there already: cl-containers, CL-XML, etc. But, whereas Java just comes with a pile of a few thousand useful classes, CL doesn\’t. The available libraries need to be collected, sorted through to see where there are still gaps as compared with other languages\’ libraries, and made 1-step retrievable (if not included in the distribution).

I started writing this a while ago, and in the meantime, Dave Robert\’s posted an article that made a very similar point, in which he decided to dive in and fill one of those gaps (a full-fledged networking library). I have spent (very little) time wrapping a few implementations\’ threading libs in the BORDEAUX-MP API.

Now I\’m stepping into the other half of the game — collecting and categorizing all the existing CL libraries, and trying to pull some of those into a competitive standard library. I\’ll post a link to my standard library comparison shortly.

Single-Dispatch\’s Win

Monday, December 12th, 2005

There is a common feature in single-dispatch OO systems that I haven\’t seen in multiple dispatch: handling of \”missing methods\”. In Ruby, it\’s method_missing(); in Perl it\’s AUTOLOAD; Smalltalk, doesNotUnderstand:; and Obj-C, forwardInvocation:. For the C++ and Java programmer, who lack such functionality, I\’ll describe it a bit:

If you define (say, in Ruby) method_missing() on a class, and a user calls a method on that class which does not exist, Ruby will pass the call to your method_missing() implementation and you\’re given the opportunity to handle the call there. This can be useful in a number of cases; one of those is where the user may expect certain things to exist as methods, but the set may be variable or unbounded. For example, creating an XML structure, and allowing the user to just assuming the existance of a method matching each element.

In Lisp (and other multiple-dispatch systems that I\’m aware of) there is no such ability. I\’ve run into a number of places where I\’ve wanted such a mechanism. I don\’t have any solution in mind to this now, but it is something that I would like to think about. And maybe get input from others about.

Typing Done Right

Saturday, September 17th, 2005

I\’m a big fan of all the sort of agile/dynamic sort of stuff. C2:TestDrivenDevelopment, C2:IterativeDevelopment, etc. But one thing I\’ve always had trouble with is accepting C2:DynamicTyping as the Right Thing. I mean, yeah, C2:ManifestTyping sucks, but C2:TypeInference is there to pick up the slack, as ML and Haskell show. With type inference, you get the clear code of dynamic typing, with the safety and performance of static typing. Which, I thought, was everything.

Yeah, I had heard the whining of those die-hard dynamicists who procliamed that there are correct programs that can not be statically typed. I didn\’t disagree, but I felt that for all practical purposes it was irrelevant. However, I\’m now working on a project where static typing gets in my way every day. It\’s unbearable.

I have a solution, which I think balances all the important bits. Yes, it\’s not perfectly \”safe\” like you static guys like, but it gives you the flexibility when you need it.

  1. type inference is key;
  2. there should be something like C2:CommonLisp\’s DECLAIM that allows you to say whether un-inferenceable bindings are errors, warnings, or ignored (and should default to errors, making the static guys happy);
  3. you can DECLARE individual bindings as dynamic, regardless of whether they\’re treated as errors.

Anyone who just wants dynamic fun DECLAIMs that un-inferenceable bindings are ignored, while others can make them warnings or errors and deal with the exceptions on a case-by-case basis. Type inference is always used whereever it is possible.

Shut up!

Monday, August 1st, 2005

So, I\’m turning off comments. Considering I get a worse than 1:5000 signal-to-noise ratio, it just wasn\’t worth my time moderating. I\’m also in the process of moving things to new software (cl-blog, written by Brian Mastenbrook), so I want to keep down the amount of content that I need to port.

I figure I should be using the Lisp tools if I want to actually bother hacking on them. One of the first things I\’ll need to add is Markdown …

Stanford: Home of McCarthyism (the good kind)

Thursday, June 16th, 2005

So, on Saturday I leave for the International Lisp Conference. I\’m pretty friggin\’ excited about it. There are a ton of cool talks scheduled, but the one I\’m most excited about is the one least-related to work.

I\’m trying to read as many lisp books as possible before I leave — make sure my brain is properly stretched before diving into such a rigorous program. I\’m going to attempt to blog about all the sessions I go to, but considering there are ten sessions each day, with a scant 10 minutes between each, it might be rough. I\’ll trackback to this entry for each of the ones I manage to talk about.