I have been trying out different values for SPWebConfigModification properties and in doing so I managed to corrupt the SPWebConfigFileChanges persisted class. This class manages the updates to web.config and persists itself to the SharePoint_Config database.
In trying out different property values I hit one that was accepted, but it caused some kind of corruption. It appears the WebConfigChildNodes property of SPWebConfigFileChanges contained an invalid node and that resulted in receiving the following error everytime I tried to update the application (using ApplyWebConfigModifications).
The node to be removed is not a child of this node.
Because the SPWebConfigFileChanges is persisted, a simple IISRESET did not clear the problem and I couldn't find a way to remove the offending item either through code or debugging. I was forced to look into the configuration database to fix the problem.
Ordinarily I would not recommend modifying the SharePoint database directly, but when there is no other way you are left with little choice.
To fix this problem you need to find the entry for the SPWebConfigFileChanges object causing the problem and change it. This can be found in the Objects table of the SharePoint_Config database. The following SQL should help with that.
SELECT Id, ClassId, ParentId, Name, Status, Version, Properties
FROM Objects
WHERE (Name LIKE '%WebConfig%')
You will need to look at the Properties column, which contains the XML for the persisted object. Once you have identified the offending item you will need to modify it, but in order to modify this table you will need to disable the triggers (right-click on each trigger and select disable). Once the two triggers are disabled perform an IISREST (to make sure the object is not in memory) and you will then be able to modify the Properties column.
Copy the entire contents of the properties column to your favorite XML editor and remove the the entry you believe to be causing the problem, then copy it back. Alternatively you can delete the entire row (as I did), but this means you may cause further problems if other changes exist. Restore the triggers and try to execute the code which was causing the problem.
This should prevent the exception and allow the code to continue.