Initial version. Needs testing.