Index: src/Actions/FillAction/FillRegularGridAction.cpp
===================================================================
--- src/Actions/FillAction/FillRegularGridAction.cpp	(revision 57dd40cda8082273cb21c69bba6a7c8b5a561fca)
+++ src/Actions/FillAction/FillRegularGridAction.cpp	(revision 42b6de7c684d4c908777f116dccaf00a8e479cf2)
@@ -20,5 +20,7 @@
 #include "CodePatterns/MemDebug.hpp"
 
+#include "Actions/UndoRedoHelpers.hpp"
 #include "Atom/atom.hpp"
+#include "Atom/AtomicInfo.hpp"
 #include "Atom/CopyAtoms/CopyAtoms_withBonds.hpp"
 #include "CodePatterns/Log.hpp"
@@ -65,7 +67,4 @@
   getParametersfromValueStorage();
 
-  // get all present atoms for UndoState
-  AtomVector presentatoms = World::getInstance().getAllAtoms();
-
   // get the filler molecule and move to origin
   const std::vector< molecule *> molecules = World::getInstance().getSelectedMolecules();
@@ -100,4 +99,5 @@
 
   // create predicate, mesh, and filler
+  std::vector<AtomicInfo> clonedatoms;
   bool successflag = false;
   {
@@ -125,6 +125,21 @@
       ClusterInterface::Cluster_impl cluster( new Cluster( filler->getAtomIds(), filler->getBoundingShape()) );
       CopyAtoms_withBonds copyMethod;
-      successflag = (*fillerFunction)(copyMethod, cluster);
+      Filler::ClusterVector_t ClonedClusters;
+      successflag = (*fillerFunction)(copyMethod, cluster, ClonedClusters);
       delete fillerFunction;
+
+      // append each cluster's atoms to clonedatoms
+      for (Filler::ClusterVector_t::const_iterator iter = ClonedClusters.begin();
+          iter != ClonedClusters.end(); ++iter) {
+        const AtomIdSet &atoms = (*iter)->getAtomIds();
+        clonedatoms.reserve(clonedatoms.size()+atoms.size());
+        for (AtomIdSet::const_iterator atomiter = atoms.begin(); atomiter != atoms.end(); ++atomiter)
+          clonedatoms.push_back( AtomicInfo(*(*atomiter)) );
+      }
+      if (!successflag) {
+        ELOG(1, "Insertion failed, removing inserted clusters again.");
+        RemoveAtomsFromAtomicInfo(clonedatoms);
+        clonedatoms.clear();
+      }
     }
 
@@ -138,24 +153,6 @@
   }
 
-  // generate list of newly created atoms
-  // (we can in general remove more quickly from a list than a vector)
-  AtomVector filleratoms = World::getInstance().getAllAtoms();
-//  LOG(0, filleratoms.size() << " atoms are present.");
-  std::list<atom *> filleratoms_list;
-  std::copy( filleratoms.begin(),  filleratoms.end(), std::back_inserter( filleratoms_list ));
-//  LOG(0, filleratoms_list.size() << " atoms have been copied.");
-  for (AtomVector::const_iterator iter = presentatoms.begin();
-      iter != presentatoms.end();
-      ++iter) {
-    filleratoms_list.remove(*iter);
-  }
-//  LOG(0, filleratoms_list.size() << " atoms left after removal.");
-  filleratoms.clear();
-  std::copy(filleratoms_list.begin(), filleratoms_list.end(), std::back_inserter( filleratoms ));
-
-//  LOG(0, filleratoms.size() << " atoms have been inserted.");
-
   if (successflag)
-    return Action::state_ptr(new FillRegularGridState(filleratoms,params));
+    return Action::state_ptr(new FillRegularGridState(clonedatoms,params));
   else
     return Action::failure;
@@ -163,29 +160,27 @@
 
 Action::state_ptr FillRegularGridAction::performUndo(Action::state_ptr _state) {
-//  FillRegularGridState *state = assert_cast<FillRegularGridState*>(_state.get());
-//
-//  BOOST_FOREACH(atom *_atom, state->filleratoms) {
-//    World::getInstance().destroyAtom(Walker);
-//  }
-//
-//  // as atoms and atoms from state are removed, we have to create a new one
-//  std::vector<atom*> filleratoms;
-//  return Action::state_ptr(new FillRegularGridState(filleratoms,state->params));
-  return Action::failure;
+  FillRegularGridState *state = assert_cast<FillRegularGridState*>(_state.get());
+
+  // remove all created atoms
+  RemoveAtomsFromAtomicInfo(state->clonedatoms);
+
+  return Action::state_ptr(_state);
 }
 
 Action::state_ptr FillRegularGridAction::performRedo(Action::state_ptr _state){
-  //FillRegularGridState *state = assert_cast<FillRegularGridState*>(_state.get());
+  FillRegularGridState *state = assert_cast<FillRegularGridState*>(_state.get());
 
-  return Action::failure;
-  //return Action::state_ptr(_state);
+  if (AddAtomsFromAtomicInfo(state->clonedatoms))
+    return Action::state_ptr(_state);
+  else
+    return Action::failure;
 }
 
 bool FillRegularGridAction::canUndo() {
-  return false;
+  return true;
 }
 
 bool FillRegularGridAction::shouldUndo() {
-  return false;
+  return true;
 }
 /** =========== end of function ====================== */
Index: src/Actions/FillAction/FillRegularGridAction.def
===================================================================
--- src/Actions/FillAction/FillRegularGridAction.def	(revision 57dd40cda8082273cb21c69bba6a7c8b5a561fca)
+++ src/Actions/FillAction/FillRegularGridAction.def	(revision 42b6de7c684d4c908777f116dccaf00a8e479cf2)
@@ -18,6 +18,6 @@
 #define paramreferences (counts)(offset)(mindistance)(SphereRadius)(RandAtomDisplacement)(RandMoleculeDisplacement)(DoRotate)
 
-#define statetypes (std::vector<atom *>)
-#define statereferences (filleratoms)
+#define statetypes (std::vector<AtomicInfo>) 
+#define statereferences (clonedatoms) 
 
 // some defines for all the names, you may use ACTION, STATE and PARAMS
Index: src/Actions/FillAction/FillSphericalSurfaceAction.cpp
===================================================================
--- src/Actions/FillAction/FillSphericalSurfaceAction.cpp	(revision 57dd40cda8082273cb21c69bba6a7c8b5a561fca)
+++ src/Actions/FillAction/FillSphericalSurfaceAction.cpp	(revision 42b6de7c684d4c908777f116dccaf00a8e479cf2)
@@ -20,4 +20,6 @@
 #include "CodePatterns/MemDebug.hpp"
 
+#include "Actions/UndoRedoHelpers.hpp"
+#include "Atom/AtomicInfo.hpp"
 #include "Atom/CopyAtoms/CopyAtoms_withBonds.hpp"
 #include "CodePatterns/Log.hpp"
@@ -82,4 +84,5 @@
 
   // create predicate, mesh, and filler
+  std::vector<AtomicInfo> clonedatoms;
   bool successflag = false;
   {
@@ -101,7 +104,23 @@
       ClusterInterface::Cluster_impl cluster( new Cluster( filler->getAtomIds(), filler->getBoundingShape() ) );
       CopyAtoms_withBonds copyMethod;
-      successflag = (*fillerFunction)(copyMethod, cluster);
+      Filler::ClusterVector_t ClonedClusters;
+      successflag = (*fillerFunction)(copyMethod, cluster, ClonedClusters);
       delete fillerFunction;
+
+      // append each cluster's atoms to clonedatoms
+      for (Filler::ClusterVector_t::const_iterator iter = ClonedClusters.begin();
+          iter != ClonedClusters.end(); ++iter) {
+        const AtomIdSet &atoms = (*iter)->getAtomIds();
+        clonedatoms.reserve(clonedatoms.size()+atoms.size());
+        for (AtomIdSet::const_iterator atomiter = atoms.begin(); atomiter != atoms.end(); ++atomiter)
+          clonedatoms.push_back( AtomicInfo(*(*atomiter)) );
+      }
+      if (!successflag) {
+        ELOG(1, "Insertion failed, removing inserted clusters again.");
+        RemoveAtomsFromAtomicInfo(clonedatoms);
+        clonedatoms.clear();
+      }
     }
+
 
     // remove
@@ -112,5 +131,5 @@
 
   if (successflag)
-    return Action::success;
+    return Action::state_ptr(new FillSphericalSurfaceState(clonedatoms,params));
   else
     return Action::failure;
@@ -118,17 +137,27 @@
 
 Action::state_ptr FillSphericalSurfaceAction::performUndo(Action::state_ptr _state) {
-  return Action::failure;
+  FillSphericalSurfaceState *state = assert_cast<FillSphericalSurfaceState*>(_state.get());
+
+  // remove all created atoms
+  RemoveAtomsFromAtomicInfo(state->clonedatoms);
+
+  return Action::state_ptr(_state);
 }
 
 Action::state_ptr FillSphericalSurfaceAction::performRedo(Action::state_ptr _state){
-  return Action::failure;
+  FillSphericalSurfaceState *state = assert_cast<FillSphericalSurfaceState*>(_state.get());
+
+  if (AddAtomsFromAtomicInfo(state->clonedatoms))
+    return Action::state_ptr(_state);
+  else
+    return Action::failure;
 }
 
 bool FillSphericalSurfaceAction::canUndo() {
-  return false;
+  return true;
 }
 
 bool FillSphericalSurfaceAction::shouldUndo() {
-  return false;
+  return true;
 }
 /** =========== end of function ====================== */
Index: src/Actions/FillAction/FillSphericalSurfaceAction.def
===================================================================
--- src/Actions/FillAction/FillSphericalSurfaceAction.def	(revision 57dd40cda8082273cb21c69bba6a7c8b5a561fca)
+++ src/Actions/FillAction/FillSphericalSurfaceAction.def	(revision 42b6de7c684d4c908777f116dccaf00a8e479cf2)
@@ -7,6 +7,6 @@
 
 // all includes and forward declarations necessary for non-integral types below
-class atom;
-
+#include <vector>
+#include "Atom/AtomicInfo.hpp"
 #include "LinearAlgebra/Vector.hpp"
 
@@ -20,6 +20,6 @@
 #define paramreferences (center)(radius)(N)(mindistance)(AlignedAxis)
 
-#undef statetypes 
-#undef statereferences 
+#define statetypes (std::vector<AtomicInfo>) 
+#define statereferences (clonedatoms) 
 
 // some defines for all the names, you may use ACTION, STATE and PARAMS
Index: src/Filling/Filler.cpp
===================================================================
--- src/Filling/Filler.cpp	(revision 57dd40cda8082273cb21c69bba6a7c8b5a561fca)
+++ src/Filling/Filler.cpp	(revision 42b6de7c684d4c908777f116dccaf00a8e479cf2)
@@ -46,13 +46,4 @@
 
 
-/** Constructor for class Filler.
- *
- * \note We store inverted \a _predicate because we need it only for
- * remove_copy_if which works in this inverted way as desired.
- *
- * @param _mesh Mesh with a NodeSet that fills its Shape
- * @param _predicate predicate construct to check at each Node
- * @param _inserter inserter which places the cloned cluster
- */
 Filler::Filler(const Mesh &_mesh, const FillPredicate &_predicate, const Inserter &_inserter) :
   mesh(_mesh),
@@ -61,21 +52,11 @@
 {}
 
-/** Destructor for class Filler.
- *
- */
 Filler::~Filler()
 {}
 
-/** Fill in the desired Cluster at each remaining node.
- *
- * \note The cluster is non-const because it is moved to the first vacant node.
- *
- * @param copyMethod functor that knows how to copy atoms.
- * @param cluster set of atomic ids contained in a specific Shape to fill each Node with
- * @return true - at least one node has been filled, false - no node filled
- */
 bool Filler::operator()(
     CopyAtomsInterface &copyMethod,
-    ClusterInterface::Cluster_impl cluster) const
+    ClusterInterface::Cluster_impl cluster,
+    ClusterVector_t &ClonedClusters) const
 {
   const NodeSet &nodes = mesh.getNodes();
@@ -126,7 +107,7 @@
 
   // clone clusters
-  std::vector<ClusterInterface::Cluster_impl> clusters(FillNodes.size());
+  ClonedClusters.resize(FillNodes.size());
   {
-    std::vector<ClusterInterface::Cluster_impl>::iterator clusteriter = clusters.begin();
+    std::vector<ClusterInterface::Cluster_impl>::iterator clusteriter = ClonedClusters.begin();
     *clusteriter = cluster;
     clusteriter++;
@@ -140,7 +121,7 @@
     // returns true, we'll have the iterator pointing at first cluster
     std::vector<ClusterInterface::Cluster_impl>::const_iterator inserteriter =
-      std::search(clusters.begin(), clusters.end(), FillNodes.begin(), FillNodes.end(),
+      std::search(ClonedClusters.begin(), ClonedClusters.end(), FillNodes.begin(), FillNodes.end(),
           boost::bind(&Inserter::operator(), boost::cref(inserter), _1, _2));
-    if( inserteriter != clusters.begin()) {
+    if( inserteriter != ClonedClusters.begin()) {
       ELOG(1, "Not all cloned clusters could be successfully inserted.");
       return false;
@@ -150,8 +131,8 @@
   // create molecules for each cluster and fill in atoms
   {
-    std::vector<molecule *> molecules(clusters.size()-1, NULL);
+    std::vector<molecule *> molecules(ClonedClusters.size()-1, NULL);
     std::generate_n(molecules.begin(), FillNodes.size()-1,
         boost::bind(&World::createMolecule, World::getPointer()) );
-    std::vector<ClusterInterface::Cluster_impl>::const_iterator clusteriter = clusters.begin();
+    std::vector<ClusterInterface::Cluster_impl>::const_iterator clusteriter = ClonedClusters.begin();
     ++clusteriter;
     std::vector<molecule *>::iterator moliter = molecules.begin();
@@ -164,8 +145,5 @@
 
   // give final statment on whether at least \a single cluster has been placed
-  if ( FillNodes.size() != 0)
-    return true;
-  else
-    return false;
+  return ( FillNodes.size() != 0);
 }
 
Index: src/Filling/Filler.hpp
===================================================================
--- src/Filling/Filler.hpp	(revision 57dd40cda8082273cb21c69bba6a7c8b5a561fca)
+++ src/Filling/Filler.hpp	(revision 42b6de7c684d4c908777f116dccaf00a8e479cf2)
@@ -14,4 +14,6 @@
 #include <config.h>
 #endif
+
+#include <vector>
 
 #include "Cluster.hpp"
@@ -32,10 +34,36 @@
 {
 public:
+  /** Constructor for class Filler.
+   *
+   * \note We store inverted \a _predicate because we need it only for
+   * remove_copy_if which works in this inverted way as desired.
+   *
+   * @param _mesh Mesh with a NodeSet that fills its Shape
+   * @param _predicate predicate construct to check at each Node
+   * @param _inserter inserter which places the cloned cluster
+   */
   Filler(const Mesh &_mesh, const FillPredicate &_predicate, const Inserter &_inserter);
+
+  /** Destructor for class Filler.
+   *
+   */
   ~Filler();
 
-  bool operator()(CopyAtomsInterface &copyMethod, ClusterInterface::Cluster_impl cluster) const;
+  //!> typedef Vector of clusters as return type for operator()
+  typedef std::vector<ClusterInterface::Cluster_impl> ClusterVector_t;
+
+  /** Fill in the desired Cluster at each remaining node.
+   *
+   * \note The cluster is non-const because it is moved to the first vacant node.
+   *
+   * @param copyMethod functor that knows how to copy atoms.
+   * @param cluster set of atomic ids contained in a specific Shape to fill each Node with
+   * @param ClonedClusters reference to vector of clusters, that is filled with created clones
+   * @return true - all clusters inserted succesfully, else - insertion failed
+   */
+  bool operator()(CopyAtomsInterface &copyMethod, ClusterInterface::Cluster_impl cluster, ClusterVector_t &ClonedClusters) const;
 
 private:
+
   //!> mesh is the set of points filling a Shape
   const Mesh mesh;
Index: src/Filling/unittests/FillerUnitTest.cpp
===================================================================
--- src/Filling/unittests/FillerUnitTest.cpp	(revision 57dd40cda8082273cb21c69bba6a7c8b5a561fca)
+++ src/Filling/unittests/FillerUnitTest.cpp	(revision 42b6de7c684d4c908777f116dccaf00a8e479cf2)
@@ -115,7 +115,9 @@
 {
   CopyAtoms_Simple copyMethod;
-  (*filler)(copyMethod, *cluster);
+  Filler::ClusterVector_t ClonedClusters;
+  (*filler)(copyMethod, *cluster, ClonedClusters);
 
   // one atom at 5 nodes added
+  CPPUNIT_ASSERT_EQUAL( mesh->getNodes().size(), ClonedClusters.size() );
   CPPUNIT_ASSERT_EQUAL( mesh->getNodes().size()*2, World::getInstance().getAllAtoms().size() );
 }
