lots of refactoring and cleanup