Archive for the 'Software Development' Category

Context Aware UI

Tuesday, January 18th, 2005

I’ve talked to a few friends about an idea that I had. I’m not very good at articulating it, so my apologies up front. So far 1 in 3 people sort of understands what I’m trying to suggest. To be honest, it’s a bit utopian, and may or may not be useful, but here goes.

I am a person who likes fluid organization. I like a bit of structure, but not a rigid structure. I find myself constantly bumping into structure all the time, and it’s somewhat aggravating. One thing that I really do despise is having to leave my environment for another just to look up a small piece of information. Here’s an example.

I come in to start the day. I open up a few consoles, and a vim session in each one. The primary session is editing the file that I actually want to work on. The other two are editing files that I’ll need to look at, header files for example, or perhaps a library reference. I constantly refer to the other two files while working on the primary file. This is good, and works well enough for me. Someone comes up and asks me about a bugzilla item. I don’t memorize each bugzilla item, so I have to leave what I’m doing, go open a browser, find the bugzilla item, go edit other source files to see what’s going on, and then answer their question. The problem is that I may have either opened up a few different windows, or taken my existing windows out of the context they are using. Let’s say that I opened a bunch of additional windows on another desktop. Now that I’ve answered their question, I don’t want to keep those windows there. However, if they come ask me again, I sure would like to get them back without having to wait for each window to open, each file to be found, etc.

Wouldn’t it be great if I could save some context along with that bugzilla item, so the next time I opened it up, I could be back to the point I was when I first did all the work?

Now before you start posting about fifteen different things that already do that, I have a question… Can I use my existing editor? Can I tie in emails, aim conversations, or whatever? If so, then yay, I’m late to the party again. If not, then do any of these solutions provide a plugin interface so I can tie in other applications?

What I’m getting at is most interfaces are tied to specific data, but they have a whole bunch of meta-data, or context to go with them. When I’m editing my primary package, I need to be able to see additional information at the same time. Whenever I’m working on that piece of code, it tends to be pretty much the same information.

It’s hard to make a concrete example of what I’m trying to think of, and all the ramifications that would result. Initially I want a bookmark for my current working environment. This would include any windows that are open, their location, their contents, etc.

Things could evolve down a road then where you could literally have an environment editor. What would this be? No idea… But what it is in my abstract little brain is something along the lines of an editor of anything. I can open up web pages, code snippets, email, shell sessions, whatever. And I can just open up different views into this meta-document. The meta-document would be the context. It would be the piece of data that associates an email with a web-page looking at bugzilla. It would be the thing that ties an aim conversation to a source file. The direct interface into this context document would be something that would have to evolve. I don’t really know what the most useful interface would be, all I know is that there is more data there than the computer is tracking now. I want the computer to be responsible for that data rather than wasting my own braincells on it.

If something like this came about, a possible evolution would be having the computer look for patterns, and perhaps suggesting environments for you. It would be nice if when someone aim’s me a question on bug #1234, and the browser automatically opens to the bug, or even better, the aim window just contains an embedded short description of the bug.
Note that there are a couple of projects that I’ve seen that are working on at least that little piece of functionality now. One is called Dashboard . It is an interesting approach, and shows some promise of being useful. However, I don’t like having yet another window open taking up real estate when 90% of the time it’s not relevant. Still, it is a very interesting project, and these guys deserve some kudos for it.

Well if you’ve gotten this far, I hope I haven’t completely lost you. If I have, then I’m sorry. Post your question, and I’ll try to clarify. If you’ve read this and said “Wow, he’s got no clue what he’s talking about!” I don’t deny it, however post your reason why. I guess it’ll be interesting to see how interfaces look in 20 years.

-Synwan

Policy Driven Development

Friday, January 7th, 2005

I was reading some stuff on aspect oriented programming. I admit, I don’t know what that is. In my pursuit of trying to find out, I stumbled upon an idea.

First a bit of backstory. I use c++ for most (ok, almost all) of my work. It’s a language I’m familiar with. It’s the language that my toolkits are available in. It’s pretty much what my fingers write by default. As a user of c++ I’ve read many book on the language. One of my favorite books is Modern C++ Design by Andrei Alexandrescu (amazon). In this book he offers a generic way to drive certain behaviors of your design implementations. He uses policies, which are small classes that drive a template class. Example: If you write a generic singleton class, you may require thread safety at times, or not. Given a policy, you can control whether thread safety code is present or not. Since you use a template, there is no cost for inheritance, virtual tables, etc. The cost is born by the compiler when it resolves the template. Go read the book for a more in depth description of the why and how behind this.

So we have policies driving fundamental behavior of our classes. In Andrei’s book, he outlines many different uses of policies, however he doesn’t seem to reuse policies that often. In his classes, there’s not really that much overlap, so this lack of reuse is understandable. In a real environment though, I believe that there is quite a bit of overlap. With a bit of forethought, I believe that policy reuse could give us an entirely new level of code reuse. Entire threading models could be available just by reimplementing policies. Memory managers could also be swapped in and out. All that would be required is a new policy, and a recompile. There would be no runtime cost, yet you would get similar benefits as inheritance. Pretty utopian, and probably not realistic, but as I’ve not tried it, perhaps it is fun to think about.

Now Andrei does have a library that he created that provides the classes he describes in Modern C++ Design. It’s called the Boost library. He very well may do what I’m describing here. I honestly haven’t looked at it much. I do intend to now though.

Anyway, that’s my thought for the day. Perhaps it’s already implemented. Perhaps it’s impractical. Perhaps it’s worth trying out. We’ll see I guess.

Oh yeah, as for aspect oriented programming, you’ll have to go google that one for yourself.

-Synwan

Interface, Interface, Interface

Wednesday, January 5th, 2005

I was talking with a friend over the holidays. He was telling me how they are always in panic mode at work. They never get time to do anything properly, and they end up being surrounded by one off hacks that never quite get the job done. He asked if I had any input to maybe mitigate this.. One word, Interfaces.

What I mean by interfaces is simply this… compartmentalize the hacks. Take five minutes and look at all the different hacks that surround you. Find two that do similar things and look closely at them. They probably have some pieces that need to do identical things (perhaps they do them in an identical way, perhaps not, doesn’t matter) If you see a common step there, then break it out into it’s own script/class/function and give it a general interface that allows both hacks to use it.

Another way to create interfaces is to create them while you’re writing your hack. Look at the task… Break the task up into it’s discreet steps. Put a facade (also known as a wrapper) around any of those steps that can be used elsewhere.

Interfaces allow you to go back and fix a portion of an application without having to go back and rewrite the entire thing. It’s an integral part of the incremental development process. Nobody has time to throw away all of their code (nor should they, but that’s a different discussion.) However any project should be in some state of rewrite continually. This is only possible when you have a general interface to compartmentalize some of the functionality.

So how do you write the general interface? Well, that comes with practice. I would start with making an interface anywhere that you think it makes sense. You will most likely create too many interfaces. It’s not hard to remove an interface, so this is of little concern. As you reuse some interfaces, but not others, you can get a feel for the interfaces that fit your problem set.

Interfaces can allow you to compartmentalize your hacks, so it is less effort to go back and clean them up. If you’re finding yourself wishing you had time to rewrite something, perhaps breaking it up into it’s parts, and putting interfaces in there will allow you to take bite-sized pieces on. You can then go back and remove any excess interfaces you had. Eventually a rewrite is just an ongoing process.

An example of this is my current project. We’ve got three people working on a KDE application that is roughly 60,000 lines long. It has been 400,000 lines before. We’ve managed to refactor it down to that level. We’re progressing to our sixth generation now. This rewrite isn’t changing too many of the internals of the app. It is, however, changing it from a monolithic multi-threaded app that used plugins to extend functionality, into several small singlethreaded apps that work together to achieve the same goal. This rewrite has taken us a little over 1 man month so far, and it’s roughly 70% complete. We’ve been doing this in between tasks for the existing system, so it’s been very sporadic as well. The codebase looks like it will end up being roughly 30,000 lines when we’re done, and it will be far simpler to debug and maintain.

We’ve gotten away with 6 rewrites (actually more like major architecture changes) because we can reuse so much of the code we’ve previously written. Our interfaces allow us to swap pieces out as needed, and when we make a bug-fix, it doesn’t affect the entire system, but just what’s behind the interface. If that component is outputting bad information that affects something outside of the interface, then it’s pretty obvious and easy to track down.

Interfaces really can allow you to isolate problem areas. You can better respond to changing needs. It allows more agile development. And best of all, you can start reusing what works, and rewriting what doesn’t!

So Here’s to interfaces!

-Synwan

Digitally signing ELF binaries.

Monday, October 4th, 2004

Ok, I’m still working on getting XMLNode ready and out as a library, but in the mean time, here’s something that’s ready, willing, and waiting.

The Intro:
A while back a project I was working on had a major architecture change. We went to a completely plugin based system. We needed a way to verify that these plugins were from a trusted source (us), unmodified, and uncorrupted. Sounds like a perfect case for digital signatures!

The Problem:
These plugins were all linux shared objects. Linux uses the ELF binary standard for all of it’s executable binary types, including executables, shared objects, and core files. The issue was how to incorporate a digital signature in such a way as to tie it to the shared object. It also needed to be straightforward enough that it didn’t run the risk of corrupting the binary. The last requirement was that it had to be lgpl since I wanted to open-source it, but it would be used for a non-gpl program.

The Solution:
Upon reading the elf spec, I found it would be fairly straight-forward to create a new section in the binary, and just put the signature there. Technically this wasn’t quite the correct and proper solution. The truly proper solution would be to insert the signature into the “notes” section. Anyway, that was a bit harder to do, and not really necessary, so I created a new section (valid and allowed in the ELF spec) to house the signature.

The Implementation:
I grabbed the very useful libcrypt library from openssl, and proceeded to find out how to programatically create RSA keys, store those keys in a format that could be used in source code, sign and verify blocks of data. Once I had that all figured out, I tackled reading and writing ELF sections in a binary. Then to tie it all together, I made a nice little app to sign binaries, and a static library that provided functions to verify signatures in a given binary. I couldn’t use the provided ELF interface because it was gpl, however there were some lower level data structures that I could use. (Thanks lgpl!)

The process for signing a binary is basically this:

  1. Read in the “data” and “text” sections of the binary, these are the compiled code sections.
  2. Sign a buffer of those combined sections with the private RSA key.
  3. Write out the resulting signature in a new section.

To verify:

  1. Read in the “data” and “text” sections of the binary.
  2. Read in the “lsesig” section.
  3. Verify the combined buffer with the signature that was read in using the public RSA key.

This effectively produces a signed binary that can be easily verified, but not easily tampered with. If you remove the signature, then the verification will fail, if you change the compiled code, the signature won’t match.

As long as you don’t distribute the private key, or the singing program, then you can verify that the shared objects you are loading came from you, weren’t tampered with, and weren’t corrupted. (Or at least didn’t have corruption in any of the code sections of the binary)

In theory this could be incorporated in the kernel to allow signed modules. It could also be used to periodically verify objects on a given system. Who knows what else it could be used for, but hey, it does what I need!

To get your hands on this uber-useful library, go to http://sourceforge.net/projects/signelf

-Synwan