address an insidious dangling reference
I still feel somewhat queasy with this whole situation! We need to return the product of the DSL/Builder by value, but we also want to swap away the current contents before starting the mutation, and we do not want a stateful lifecycle for the mutator implementation. Which means, we need to swap right at construction, and then we copy -- TADAAA! Thus I'm going for the solution to disallow copying of the mutator, yet to allow moving, and to change the builder to move its product into place. Probably should even push this policy up into the base class (TreeMutator) to set everyone straight. Looks like this didn't show up with the test dummy implementation just because in this case the src buffer also lived within th TestMutationTarget, which is assumed to sit where it is, so effectively we moved around only pointers.
This commit is contained in:
parent
adf01b0fbf
commit
c49dd04b44
3 changed files with 18 additions and 2 deletions
|
|
@ -174,6 +174,7 @@
|
|||
using Iter = typename BIN::iterator;
|
||||
|
||||
BIN binding_;
|
||||
public: ///////////////TODO: diagnostics
|
||||
Iter pos_;
|
||||
|
||||
|
||||
|
|
@ -184,8 +185,19 @@
|
|||
, pos_(binding_.initMutation())
|
||||
{ }
|
||||
|
||||
ChildCollectionMutator (ChildCollectionMutator&&) =default;
|
||||
ChildCollectionMutator (ChildCollectionMutator const&) =delete;
|
||||
ChildCollectionMutator& operator= (ChildCollectionMutator const&) =delete;
|
||||
|
||||
|
||||
/////////////////TODO : diagnostics
|
||||
typename BIN::const_iterator
|
||||
exposeSrcBuffer() const
|
||||
{
|
||||
return eachElm (binding_.contentBuffer);
|
||||
}
|
||||
/////////////////TODO : diagnostics
|
||||
|
||||
/* ==== re-Implementation of the operation API ==== */
|
||||
|
||||
/** skip next pending src element,
|
||||
|
|
|
|||
|
|
@ -333,8 +333,8 @@ namespace diff{
|
|||
struct Builder
|
||||
: PAR
|
||||
{
|
||||
Builder(PAR par)
|
||||
: PAR(par)
|
||||
Builder(PAR&& par)
|
||||
: PAR(std::forward<PAR>(par))
|
||||
{ }
|
||||
|
||||
template<class CLO>
|
||||
|
|
|
|||
|
|
@ -354,6 +354,7 @@ namespace test{
|
|||
CHECK (isnil (contents));
|
||||
|
||||
cout << "injected......" << join(target) <<endl;
|
||||
cout << "exhausted....." << join(mutator.exposeSrcBuffer()) <<endl;;
|
||||
|
||||
|
||||
// --- second round: reorder the collection ---
|
||||
|
|
@ -376,6 +377,9 @@ namespace test{
|
|||
}));
|
||||
|
||||
CHECK (isnil (target)); // the "visible" new content is still void
|
||||
cout << "target......" << join(target) <<endl;;
|
||||
cout << "srcBuff....." << join(mutator2.exposeSrcBuffer()) <<endl;;
|
||||
cout << "pos_........" << *mutator2.pos_ <<endl;;
|
||||
|
||||
CHECK (mutator2.matchSrc (ATTRIB1)); // current head element of src "matches" the given spec
|
||||
CHECK (isnil (target)); // the match didn't change anything
|
||||
|
|
|
|||
Loading…
Reference in a new issue