mr-edd.co.uk http://www.mr-edd.co.uk Horsing around with the C++ programming language http://www.mr-edd.co.uk/static/rss.png http://www.mr-edd.co.uk Copyright Edd Dawson Tue, 24 Apr 2012 00:00:01 GMT 720 Another use for explicit vtables http://www.mr-edd.co.uk/blog/another_use_for_explicit_vtables In my previous post I outlined a technique whereby coupling could be reduced by way of creating a pseudo-vtable. I've since realised that this technique can also be used to help create an efficient representation for polymorphic types with value semantics. Consider this base class, which we might use as the root of a polymorphic class hierarchy in a computer game:struct monster { virtual ~monster(); virtual void attack(player &target); }; Such polymorphic hierarchies will typically imply dynamic allocation somewhere along the line. For example, we typically won't create a std::vector<monster> because we can't store derived monster objects by value in containers without slicing. Instead, we'll have to do something like keep a container of (smart) pointers, or use a smart container such as boost::ptr_vector<monster>, which in turn means we'll probably have to allocate our derived monster objects on the heap. The large number of small allocations implied by this approach can be detrimental in a number of ways; some of the locality benefits we may have got with a vector<> have been lostdepending on the quality and characteristics of our allocator due to the monsters now being dotted around the heap. The allocations themselves can be detrimental to performance, especially if frequent. Contention within allocation routines running in multi-threaded applications can exacerbate this problem. Let's see how we might avoid these problems by adapting the explicit vtables technique described previously. Tue, 24 Apr 2012 00:00:01 GMT Nifty little lock class http://www.mr-edd.co.uk/blog/nifty_little_lock Happy new(?) year! Ok, ok, so I haven't written in a while. I've been meaning to finish of the series on undo/redo for some time now. Hopefully I'll get that put to bed at some point, but in the meantime I'll try to get the ball rolling with something smaller. If you've written any code that uses low-level threading primitives such as mutexes, you'll likely/hopefully be aware of the 'scoped-locking' idiom. In short, it looks something like this:void some_function(mutex &m) { lock lk(m); // calls m.acquire(); // ... // lk's destructor calls m.release(). } It ensures that a lock is always released, regardless of whether the scope is left via a return statement, or due to an exception. This is a nice way to statically ensure that you don't accidentally leave a mutex in an acquired stateMany will likely recognise this as an instance of the RAII idiom. But it's quite often the case that a threading library will offer a selection of different mutex types to choose from. Each mutex will offer the same core interface: acquire() and release(). What typically happens, therefore, is that the lock class is becomes a template with the type of mutex as a template-parameter. This in turn means that the creation of the lock object can take a bit more typing than we might like:void some_function(recursive_mutex &m) { lock<recursive_mutex> lk(m); // ... } On its own that's not too bad, but any function that once took a reference to a lock object as a parameter may now have to become a template function in order to accept arbitrary lock types, possibly increasing compile times as a side-effect. This is the case with some of the methods on boost::condition_variable, for example. Here's a simple but cunning technique for overcoming these problems: Thu, 08 Mar 2012 00:00:01 GMT _GLIBCXX_DEBUG is broken on Apple's GCC 4.2 http://www.mr-edd.co.uk/blog/osx_gcc42_glibcxx_debug_is_br0ken Upgraded to Lion recently and hit this issue rather quickly. Just slapping it here for those Googling around the issue. The definition of _GLIBCXX_DEBUG seems to affect the C++ standard streams particularly badly. More: https://discussions.apple.com/message/10244440?messageID=10244440#10244440?messageID=10244440 EDIT: specifically it appears to occur when building against the 10.6 and 10.7 SDKs I've also had some trouble with the XCode 4's ar and the compiler also issues lots of annoying warnings about the inability to "add line info to anonymous symbol"s. Somewhat underwhelmed by both Lion and XCode 4's tools so far :/ Thu, 11 Aug 2011 00:00:01 GMT Undo/redo part 3: combining actions http://www.mr-edd.co.uk/blog/undo_redo_3_combining_actions Previously in this undo/redo series we've looked at: how to set up a basic action interface and a simple undo_stack classhow exception safety guarantees of actions affect the undo_stack's implementationIn this episode, I'd like to look at how to efficiently combine two or more actions in to a single compound action and why we might want to do so. I guess this topic wanders back in to the realms of what others articles have discussed before when looking at undo/redo. We'll see however, that exception safety will come back in to the picture briefly, which is something all other articles I've read seem to neglect. Tue, 08 Feb 2011 00:00:01 GMT Strange GCC error: expected unqualified-id before ‘OTHER’ token http://www.mr-edd.co.uk/blog/unqualified_id_before_other A brief interlude in the undo/redo series. Just posting this here so that Google can index the answer. Today, we were seeing a strange error coming from one of our source files when compiled with Apple's g++ 4.0.1: error: expected unqualified-id before ‘OTHER’ tokenThe problem here is that the file has a byte order mark, which g++ doesn't seem to like (at least this not flavour of g++, anyway). If you happen to be using Vim, this should fix it, I think: :setlocal nobomb :w Fri, 28 Jan 2011 00:00:01 GMT Undo/redo part 2: exception safety http://www.mr-edd.co.uk/blog/undo_redo_2_exception_safety Ok, so on with the second installment of the N-part series on undo/redo mechanisms. Last time we introduced the action base class and an elementary undo_stack. I claimed that those were the easy bits, or at the very least, the only parts of an undo-supporting-application that anyone has cared to talk about on the web so far. So we'd better start looking at some of the harder parts now. In this episode: exception safety. Wed, 19 Jan 2011 00:00:01 GMT Undo/redo part 1: the easy bits http://www.mr-edd.co.uk/blog/undo_redo_1_easy_bits First of all: happy new year! Better late than never, I suppose :) In my current project at work, we've been looking in to and exploring various implementations of undo/redo. A web-search yields plenty of results, each eagerly telling you how to use the command pattern to create undo-able tasks and put them in to some kind of undo stack container. This is all well and good, but from where I'm standing, implementing the command pattern for undo/redo and rustling up an undo_stack class is the easy bit. What I struggled to find were any notes on the implications for an application's data model, given that most or all mutations have to be undo-able. This is the hard bit of implementing undo/redo, I think. It's what our team has been discussing recently and it is these implications that I want to get around to discussing in subsequent posts. We might even end up with a little library by the end of this series. We'll see Unfortunately, this will be another one of those articles that runs through the implementation of an undo stack, but I just want to get this down quickly so that we can refer back to it in follow-up posts of the series. Sun, 16 Jan 2011 00:00:01 GMT sigfwd 0.1.1 and fungo 0.1.2 http://www.mr-edd.co.uk/blog/sigfwd_0_1_1_and_fungo_0_1_2 I've tagged sigfwd version 0.1.1 and fungo version 0.1.2 over the last couple of days due to problems discovered in the field. sigfwd now has much better support for connecting Qt signals to functors created with boost::bind. It also behaves a bit better when compiled against older versions of boost. A colleague discovered a compilation error in fungo that arises on systems where sizeof(unsigned) < sizeof(void*). Thanks, Jo! Fri, 03 Dec 2010 00:00:01 GMT Setting Qt::WA_MacSmallSize automatically for the whole application http://www.mr-edd.co.uk/blog/automatic_wa_macsmallsize In recent years Qt has made significant advancements in ensuring it looks and behaves natively on OS X. It still has some way to go, but it's undoubtedly heading in the right direction. However, with a little bit of care I think you can just about get to a point where even the most hardened Mac zealot would struggle to tell that Cocoa isn't being used underneath. One thing that hinders Qt's ability to blend in to its surroundings on an OS X desktop is the default font size used in many of the widgets. It's possible to fix this by calling widget->setAttribute(Qt::WA_MacSmallSize) (or similar) on the widgets in question, but it sucks to have to write that everywhere. So today I decided to see if I could find a workaround using Qt's styling system. Unfortunately, I started to go cross-eyed rather quickly. However, I did eventually come up with a solution via another mechanism. It's a bit of a hack and time will tell whether or not it should remain in our application's code, but it might be useful to share it because it does at least work. Thu, 02 Dec 2010 00:00:01 GMT jpegxx 0.3.1 bugfix release http://www.mr-edd.co.uk/blog/jpegxx_0_3_1 I've recently updated jpegxx to fix a bug caused by some experimental code that I accidentally committed to the code repo :/ The offending changeset can be found here. Unfortunately these problems are present in the 0.3.0 release. If you were using jpegxx with a build of the IJG JPEG library (aka libjpeg) that was created with a C++ compiler, then you won't be affected by the problem. However, I still recommend upgrading to the recently tagged 0.3.1 release. The new version requires no changes to client code so you should be able to drop it in to existing projects. Fri, 12 Nov 2010 00:00:01 GMT