Day 2 of AusHac2010 is coming to an end, and we’ve made a lot of progress:
• Bernie Pope has been making great progress with a new MPI binding for Haskell
• Ben Lippmeier, Erik de Castro Lopo and Ben Sinclair have been busily hacking on DDC, with 13 commits today alone
• Stephen Blackheath has been working on some code using the Accelerate library that rasterises triangles for use in a commercial computer game.
• Hamish Mackenzie, Jens Petersen and Matthew Sellers have been working on better Yi integration for Leksah, working on using Yi’s current configuration file, and improving “launch experience”, focusing on eliminating the requirement of creating an initial workspace file.
• Lang Hames has been using his experience with LLVM from working at Apple as an intern to improve various low level problems in LLVM. His work should help resolve some of the problems the LLVM backend to GHC has, but should also be very beneficial to many other LLVM users. While doing this, he’s written a very nice tool that illustrates register liveness, with further work focusing on colouring the HTML output to show register pressure. The LLVM guys seem quite excited about this work, which is great.
• Mark Wotton and Sohum Banerjea have been trying to extend Hubris, the Haskell-Ruby bridge, to work with polymorphic functions. Their heads are quite sore from all the head banging. Raphael Speyer has been working on an install script to make installation much easier for users.. but only if you use Ubuntu so far.
• Ivan Miljenovic has been prematurely optimising his containers library, before finalising the API. This library is designed to let library writers leave the choice of which container data structure to output to the library consumer as well as making it easier to change which data structure you want to use in your code, with minimal code change. See his blog post for more details.
• Trevor McDonell has been working on the CUDA backend to Accelerate, adding support for efficient nested tuple types, and other bug fixes. Sean Lee has been helping out with testing of this code, along with Manuel Chakravarty.
With one more full day to go, I think we’ll be getting a lot of awesome work done tomorrow!
So, the first half day of AusHac2010 was yesterday. We had about 12 people turn up, which isn’t too bad for a Friday.
Erik de Castro Lopo did a lot of work on Ben Lippmeier’s DDC compiler for his Disciple language.
There was some initial work on the Accelerate library for accelerated array computations in Haskell, using various backends. Most of the current work is aiming at making the CUDA backend usable, after which more backends will likely be added, such as an LLVM backend, and possibly an OpenCL backend as well.
Due to the restricted time yesterday, not all that much work was started, but day 2 (see my next post!) has been much more productive.
I was taking a look at google analytics today, and decided to take a look at the browser percentages. I was a little surprised when I saw the results; 60.1% Firefox, 13.9% Safari, 7.9% Mozilla, 5.9% Opera, 5.5% Chrome, and 2.9% Internet Explorer, since the beginning of the year. The sort of crowd that read my blog I’d expect to be using Firefox, but maybe not such a high percentage. Pretty pleased that Safari is in second, and not totally sure what Mozilla is, but probably just the other mozilla based browsers like IceWeasel. Also a little surprised with the amount of Opera users, but not too much. But the biggest surprise was IE, I never expected I’d get so few IE users, and I’m very happy about this!
Even though I have taken to not hacking my site so much, I’m still pleased that I can basically ignore having to even try making my site IE compatible. I know I’m likely to get some responses to this saying that I should still do it, but you know what? Screw that! if people are stupid enough to still be using IE (even if it has improved in some very good ways in recent times), then I don’t care what sort of experience they have on my site. They’re in the vast minority, and they annoy me, so stuff ‘em.
Yep, not a terribly indepth or interesting post, I know, but I needed to post something… my hits were dropping!
‘Till next time,
– Axman
Yesterday, I submitted my first program modification to the computer language shootout game, which is a change to the thread-ring program. If you’ve followed the shootout at all, you will probably know that haskell dominates at this benchmark, with the next contender (Mozart/OZ) being 50% slower than haskell already.
While i was having a look at the code, I noticed that the haskell entry was forkIO’ing a lot of threads, which is exactly what we want. But we weren’t quite forking enough; one of the 503 threads was the main thread. Bad idea!
I learnt a few weeks ago, while working on my AVar package, that communicating between bound and non bound threads (forkIO’d vs. main) when using things like MVars can be really slow. And this is exactly what was happening:
main = do a <- newMVar . read . head =<< getArgs z <- foldM new a [2..ring] thread 1 z a
as you can see, the last/first thread was being run in main, so once per loop around the ring, we were talking to main via an MVar, and then talking to another forkIO’d thread via another MVar. So here’s what I did:
main = do a <- newMVar . read . head =<< getArgs z <- foldM new a [2..ring] ret <- newEmptyMVar forkIO (thread 1 z a >>= putMVar ret) takeMVar ret
Two and a half lines of code. What were the results? Well, when the program was run with n = 50,000,000, the original ran in ~14.2s, with -N{1,2,3,4}, my modified one took on average ~9.3s, which is about a 33% improvement. It should be noted that when both programs are compiled without -threaded, there is almost no difference in speed at all (and they both run considerably faster than the non threaded version). Need to talk to the shootout peeps and find out if it’s against the rules to compile without -threaded, and get an even more massive speed boost.
It’s Friday night, and I have just finished my first week of my second year at the Australian National University. This is the reason I haven’t written anything here for the last week, and my blog rate will probably remain low for the next 10 weeks… but I’ll do my best! This semester I’m doing some rather interesting courses (and some not so much…)
COMP2300 – Introduction to Computer Systems Which is about.. well computer systems. It covers topics like binary representations of numbers, C, computer architecture, etc. The thing I am however most looking forward to the most will be the third assignment, which will be based around the uni’s new T2 (the one Ben Lippmeier is using for most of his GHC on SPARC work)
COMP2100 – Software Construction This seems to be more about how to write larger software, than actual programming (though it does emphasise programming weekly to get into good habits). I’m interested to see for the Personal Software Process (PSP) stuff goes, it seems to me that it can make you a more productive programmer quite easily. After only an hour of using the time keeping for it, i’ve noticed i don’t get distracted as much, because it’s not programming time, so all i do is program in this time. Means i distract myself less, which is very helpful.
ENGN2211 – Electronic Circuits This is a second year electronics course, and should be fairly interesting too. Not much to say about this one…
ENGN2226 – Engineering Systems Analysis This course is taught by a pretty cool German maths PhD, and focuses mostly on modelling systems, which is obviously an integral part of engineering. We’ll have to use MATLAB for this, which from what I’ve heard from others may not be very fun at all. Could be a good place to use some of the nice statistical packages for haskell…
Anyway, I’ll try and keep up with the haskelling, but I’ll be doing a lot of non haskell this semester (C, Java, ASM, MATLAB), so it may have to fall by the way side for now
Yesterday, i stuck AVar 0.0.4 on hackage. Again, not thinking things through as well ad i should have, i realised later it should have been the 0.1.0 release, since it was the first major change to the package since i first wrote it.
So what’s new? Well, i split it up a bit, into three modules: Data.AVar, the classic interface, Data.AVar.Unsafe, the same as Data.AVar, but it throws any exceptions encountered by the variable, instead of passing them back to the user, and Data.AVar.Internal, which contains the code for the actual for AVars, and the datatypes used by them.
I think this is a nice way of doing things, and hopefully will make using the system a little easier if you don’t expect to cause exceptions. So as always, if you have any suggestions, please let me know.
The other day, I put my AVar package on hackage. Doing so taught me more than i expected it would, mainly that i need to do more testing of cabal packages before submitting them, and also to make sure you’ve exported all the functions you need to actually use the package (I forgot to put putAVar in the module exports -_-). So i’m up to release 0.0.3, without much work being done at all (although, I can’t think of much more to do really).
With the current release, i think that all exceptions that may occur from functions passed by the user to the variable should be caught by and handled correctly by the variable. I guess in a sense, AVars are smart variables that know what is and isn’t good for them, and will refuse to hurt themselves (hopefully!).
If you’re interested in seeing what AVar can do, check out the Hackage page. I really have no idea how it might be useful, but I’d love to hear others thoughts on it. If you have any requests, please let me know, and I’ll see what I can do (proper transactional … transactions are not something I want to tackle, especially with uni starting on monday)
Today, I’ve been talking with some people in #haskell about this ASTM thing, and I’ve had some great input, mainly from Stefan Ljungstrand (ski on #haskell), along with quicksilver and Simon Marlow, and I thought I’d share the changes I’ve put in with their help. I’m still not sure how useful this stuff is, but it’s fun and I’m learning. If you’re wondering what i’m on about, see this post.
So, the new features I’ve added are mainly to do with exception handling, so that variables don’t ‘die’ if you call tail on [], they report the error, and don’t change the ’state’. I’ve also deleted the Swap constructor, and replaced it with a more general Mod’ constructor:
data Transaction a = Put a | Get (MVar a) | Mod (a -> a) (MVar (Maybe E.SomeException)) | forall b. Mod' (a -> (a,b)) (MVar (Either E.SomeException b)) | Atom (a -> Bool) (a -> a) (a -> a) (MVar Bool)
This you provide a function which takes the current ’state’, possibly modifies it, and returns something else, and return that something else back to you. This works a lot like the State monad, but allows concurrency.
I’ve changed handler as well to look like this:
handler :: Chan (Transaction a) -> a -> IO b handler chan !x = do req <- readChan chan case req of Put a -> handler chan a Get mvar -> do putMVar mvar x handler chan x Mod f mvar -> do let x' = f x p <- E.catch (E.evaluate x' >> return Nothing) (\e -> return (Just e)) putMVar mvar p case p of Nothing -> handler chan x' _ -> handler chan x Mod' f mvar -> do let y@(a,b) = f x p <- E.try (E.evaluate a >> E.evaluate b) case p of Right _ -> do putMVar mvar (Right b) handler chan a (Left e) -> do putMVar mvar (Left e) handler chan x Atom test y n res -> if test x then do putMVar res True handler chan (y x) else do putMVar res False handler chan (n x)
As you can see, I’ve added some exception handling, but I still need to add some more to the Atom/condModAVar case. What I want is something that can keep running even after there’s been an exception. I mean, who wants a mutable variable to just stop working huh?. I think once I get that done, along with haddock docs, I’ll stick it on hackage.
So, tonight, I had an idea for something that I’m not sure if it’s either useful, efficient, interesting or anything other than a waste of time. It was an idea for the emulation of mutable variables, using functions as a way of storing the values in an accumulating parameter of sorts. They could safely be shared between threads, and could (and sort of do) support atomic actions.
It turned out to be really simple to implement, and I think just showing you the code would explain what I’m on about more than anything else. I don’t know how else this could be extended (I’m sure it could be though, for some fairly interesting ideas), and since it has been written in the wee hours of the morning, I may be doing some pretty stupid stuff…
So, I’d love to hear some discussion (though yes, I do already know this could probably be done with MVars or TVars or what have you) and ideas, and here’s the code:
module ASTM where import Control.Concurrent import Control.Concurrent.MVar import Control.Concurrent.Chan data Transaction a = Put a | Get (MVar a) | Mod (a -> a) | Atom (a -> Bool) (a -> a) (a -> a) (MVar Bool) data AVar a = AVar (Chan (Transaction a)) newAVar :: a -> IO (AVar a) newAVar x = do chan <- newChan :: IO (Chan (Transaction a)) forkIO (handler chan x) return (AVar chan) where handler chan x = do req <- readChan chan case req of Put a -> handler chan a Get mvar -> do putMVar mvar x handler chan x Mod f -> handler chan (f x) Atom test y n res -> if test x then do putMVar res True handler chan (y x) else do putMVar res False handler chan (n x) putAVar (AVar chan) x = writeChan chan (Put x) modAVar (AVar chan) f = writeChan chan (Mod f) getAVar (AVar chan) = do res <- newEmptyMVar writeChan chan (Get res) takeMVar res condModAVar (AVar chan) p t f = do res <- newEmptyMVar writeChan chan (Atom p t f res) takeMVar res
So I’ve been trying to see if I could speed up the pidigits program, and, well, failed. I’m not alone though, Stephen Blackheath and others have tried too, and no one’s managed to make things much, if at all faster. The main problem seems to be that GHC is allocating a lot of RAM, which must be related to the need for Integers. The current program uses up 500+MB by the time it finishes. Not good. So, I’m putting a call out to see if anyone else can either think of a better way to get the answer than the current entry, or any tips about reducing memory usage. If you come up with anything, I’d love to hear from you. Cheers, ~ Axman