--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/webservices/wsstar/wsstarpolicy/src/PolicyNormalizer.cpp Thu Jan 07 16:19:19 2010 +0200
@@ -0,0 +1,1466 @@
+/*
+* Copyright (c) 2006-2006 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description:
+*
+*/
+
+
+
+
+// INCLUDE FILES
+#include <f32file.h>
+#include "PolicyNormalizer.h"
+#include "SenXmlElement.h"
+#include "WSPolicyRegistry.h"
+
+using namespace WSPolicy;
+
+namespace
+{
+_LIT( KOutPath, "c:\\logs\\out.xml");
+_LIT8(KColon, ":");
+//_LIT8( KServicePolicyLocalName, "ServicePolicy");
+}
+
+
+
+CPolicyNormalizer* CPolicyNormalizer::NewL()
+ {
+ CPolicyNormalizer* pSelf =
+ CPolicyNormalizer::NewLC();
+ CleanupStack::Pop(pSelf);
+ return pSelf;
+ }
+
+CPolicyNormalizer* CPolicyNormalizer::NewLC()
+ {
+ CPolicyNormalizer* pSelf =
+ new (ELeave) CPolicyNormalizer();
+ CleanupStack::PushL(pSelf);
+ pSelf->ConstructL();
+ return pSelf;
+ }
+
+CPolicyNormalizer::~CPolicyNormalizer()
+{
+ delete iXmlReader;
+ delete iPath;
+ delete iNewPolicy;
+ iOrphanElements.ResetAndDestroy();
+}
+
+CPolicyNormalizer::CPolicyNormalizer()
+ {
+ }
+void CPolicyNormalizer::ConstructL()
+ {
+// BaseConstructL(KServicePolicyLocalName());
+ iXmlReader = CSenXmlReader::NewL();
+ iNewPolicy = CSenXmlElement::NewL(KWsPolicy);
+ count = 0;
+ }
+
+
+
+CSenElement* CPolicyNormalizer::NormalizeL(CPolicyRegistry* aRegistry)
+{
+
+ CSenElement& element = AsElement();
+ TPtrC8 name = element.LocalName();
+
+ if (name.Compare(KWsPolicy) == 0)
+ {
+ iNewPolicy->CopyFromL(element);
+
+ RPointerArray<CSenElement>& children = iNewPolicy->ElementsL();
+ CleanupClosePushL(children);
+ TInt childCount = children.Count();
+
+ if(childCount > 0)
+ {
+ CSenElement* pNextChild;
+ TInt i = 0;
+
+ while (i < childCount)
+ {
+
+ pNextChild = children[childCount-1];
+ CSenElement* newElement = iNewPolicy->RemoveElement(*pNextChild);
+ delete newElement;
+ childCount--;
+ }
+
+ }
+ CleanupStack::PopAndDestroy(); //children
+ ProcessPolicyReferenceL(&element, aRegistry);
+ ProcessPolicyTermL(&element, iNewPolicy);
+ ProcessLogicL(iNewPolicy);
+ ProcessAssertionBranchingL(iNewPolicy);
+
+//#ifdef _SENDEBUG
+ WriteL(iNewPolicy);
+//#endif
+ return iNewPolicy;
+ }
+
+ return NULL; //&element;
+
+}
+
+TPtrC8 CPolicyNormalizer::GetReferenceUriL(CSenElement* aReference)
+ {
+ RPointerArray<CSenBaseAttribute>& attrs = aReference->AttributesL();
+
+ CSenBaseAttribute* bs = NULL;
+ TInt ele_count = attrs.Count();
+
+ for (TInt j=0; j < ele_count; j++)
+ {
+
+ bs = (attrs)[j];
+ if(bs->Name().Compare(KUri) == 0)
+ {
+ return bs->Value();
+ }
+
+
+ }
+ return KNullDesC8();
+ }
+
+TInt CPolicyNormalizer::ReplacePolicyReferenceL(CSenElement* aReferenceElement, CSenElement* aReferredPolicy)
+ {
+ //get the parent of policy, remove referenceElement and add referred policy there
+
+ CSenElement* parent = aReferenceElement->Parent();
+
+ if(!parent)
+ return KErrNotFound;
+ //add all policy child elements here and then copy those element's contents
+ //from referred policy,
+ //the referred policy element is owned by SD so do not use it
+
+ RPointerArray<CSenElement>& children = aReferredPolicy->ElementsL();
+ TInt childCount = children.Count();
+
+ if(childCount > 0)
+ {
+ CSenElement* pNextChild;
+ TInt i = 0;
+
+ while (i < childCount)
+ {
+
+ pNextChild = children[i];
+ TPtrC8 localName = pNextChild->LocalName();
+ TPtrC8 nsUri = pNextChild->NamespaceURI();
+ CSenElement& newElement = parent->AddElementL(nsUri, localName);
+ newElement.CopyFromL(*pNextChild);
+ i++;
+ }
+ }
+
+//now we have resolved the reference so we dont need the PolicyReference element
+ CSenElement* removed = parent->RemoveElement(*aReferenceElement);
+
+ if(removed)
+ {
+ delete removed;
+ return KErrNone;
+ }
+ return KErrNotFound;
+ }
+
+CSenElement* CPolicyNormalizer::ProcessPolicyReferenceL(CSenElement* aPolicy, CPolicyRegistry* aRegistry)
+{ //Loop for wsp:PolicyReference element and if found then replace
+ // it with wsp:All and copy everything from found policy to here
+ if(aRegistry == NULL)
+ return NULL;
+ //Check if there is a reference if yes then resolve it
+ RPointerArray<CSenElement> referenceChildren;
+
+ if(aPolicy->ElementsL(referenceChildren, KWsPolicyReference) == KErrNone)
+ {
+ TInt childCount = referenceChildren.Count();
+ TInt i = 0;
+ CSenElement* pNextChild;
+
+ while (i < childCount)
+ {
+ pNextChild = referenceChildren[i];
+ TPtrC8 localName = pNextChild->LocalName();
+ TPtrC8 uri = GetReferenceUriL(pNextChild);
+ _LIT8(KHash, "#");
+
+ HBufC8* aRippedUri = NULL;
+
+ if(uri.Left(1).Compare(KHash) == 0)
+ aRippedUri = uri.Right(uri.Length()-1).AllocL();
+
+ if(aRippedUri->Length() > 0)
+ {
+ CSenElement* referedPolicy = aRegistry->LookupPolicy(aRippedUri->Des());
+ if(referedPolicy)
+ {
+ ReplacePolicyReferenceL(pNextChild,referedPolicy);
+ }
+ }
+ delete aRippedUri;
+
+ i++;
+ }
+ }
+
+ //Check in all children recursively PolicyReferences and resolve them
+ RPointerArray<CSenElement>& children = aPolicy->ElementsL();
+ TInt childCount = children.Count();
+
+ CSenElement* pNextChild;
+ TInt i=0;
+
+ while (i < childCount)
+ {
+ pNextChild = children[i];
+ TPtrC8 localName = pNextChild->LocalName();
+ ProcessPolicyReferenceL(pNextChild, aRegistry);
+ i++;
+ }
+
+ return NULL;
+}
+
+TBool CPolicyNormalizer::IsOptionalL(CSenElement* aAssertion)
+{
+ // 7, 21, 23, 24
+ RPointerArray<CSenBaseAttribute>& attrs = aAssertion->AttributesL();
+
+ CSenBaseAttribute* bs = NULL;
+ TInt ele_count = attrs.Count();
+
+ for (TInt j=0; j < ele_count; j++)
+ {
+
+ bs = (attrs)[j];
+ if(bs->Name().Compare(KWspOptinal) == 0)
+ {
+ if(bs->Value() == KWspOptinalTrue)
+ return ETrue;
+ }
+
+
+ }
+ return EFalse;
+}
+
+CSenElement* CPolicyNormalizer::ProcessOptionalElement(CSenElement* /*aAssertion*/, CSenElement* aNormalAssertion)
+ {
+ return aNormalAssertion;
+ }
+
+CSenElement* CPolicyNormalizer::ProcessAssertionTermL(CSenElement* aAssertion, CSenElement* aNormalAssertion)
+{
+ TPtrC8 assertionName = aAssertion->LocalName();
+ TPtrC8 assertionNsUri = aAssertion->NamespaceURI();
+ TPtrC8 nsPrefix = aAssertion->NsPrefix();
+ TBuf8<255> qname(nsPrefix);
+ qname.Append(':');
+ qname.Append(assertionName);
+ CSenElement& newNormalForm = aNormalAssertion->AddElementL(assertionNsUri,assertionName, qname);
+
+ if(IsOptionalL(aAssertion))
+ {
+ if (CopySenElementWithoutOptionL(aAssertion, &newNormalForm))
+ {
+ CSenElement* parent = aNormalAssertion->Parent();
+ AddAndElementL(parent);
+ }
+ }
+ else
+ {
+ CopySenElementL(aAssertion, &newNormalForm);
+ }
+
+
+
+
+ RPointerArray<CSenElement>& children = aAssertion->ElementsL();
+ TInt childCount = children.Count();
+
+ if (childCount > 0)
+ {
+ CSenElement* pNextChild;
+ TInt i =0;
+ while (i < childCount)
+ {
+
+ pNextChild = children[i];
+ TPtrC8 localName = pNextChild->LocalName();
+
+
+ if(localName.Compare(KXorCompositeAssertion) == 0)
+ {
+
+ }
+ else if (localName.Compare(KAndCompositeAssertion) == 0)
+ {
+
+ }
+ else if (localName.Compare(KWsPolicy) == 0 )
+ {
+ CSenElement* aNewElement = AddPolicyElementL(&newNormalForm);
+ aNewElement = ProcessPolicyTermL(pNextChild,aNewElement);
+
+ }
+ else
+ {//if asserion is not well defined and dont have apolicy object here
+ //then it should add one and then add XOR and AND
+// CSenElement* aNewElement = AddPolicyElementL(&newNormalForm);
+// CSenElement* pChildXor = AddXorElementL(aNewElement);
+// CSenElement* pChildAnd = AddAndElementL(pChildXor);
+ aNormalAssertion = ProcessAssertionTermL(pNextChild, &newNormalForm);
+ }
+
+ i++;
+ }
+ }
+
+ return aNormalAssertion;
+}
+
+CSenElement* CPolicyNormalizer::ProcessPolicyTermL(CSenElement* aAssertion, CSenElement* aNormalAssertion)
+{
+
+ RPointerArray<CSenElement>& children = aAssertion->ElementsL();
+ TInt childCount = children.Count();
+ CSenElement* pNextChild;
+
+ if(childCount == 0)
+ {
+ CSenElement* pXor = AddXorElementL(aNormalAssertion);
+ CSenElement* pAnd = AddAndElementL(pXor);
+ return aNormalAssertion;
+ }
+ TInt i=0;
+
+ CSenElement* assertionParent = aNormalAssertion;
+
+
+ while (i < childCount)
+ {
+ pNextChild = children[i];
+
+
+ TPtrC8 localName = pNextChild->LocalName();
+
+ if(localName.Compare(WSPolicy::KXorCompositeAssertion) == 0)
+ {
+ TPtrC8 nt = aNormalAssertion->LocalName();
+
+ if(nt.Compare(WSPolicy::KWsPolicy)== 0) //PERFECT we need it
+ {
+ // aNormalAssertion =
+ ProcessXORTermL(pNextChild,aNormalAssertion);
+ }
+
+ else if(nt.Compare(WSPolicy::KXorCompositeAssertion)== 0)
+ {
+ CSenElement* NewXorParent = aNormalAssertion->Parent();
+ ProcessXORTermL(pNextChild,NewXorParent);
+ }
+ else if(nt.Compare(WSPolicy::KAndCompositeAssertion)== 0)
+ {
+ CSenElement* NewXorParent = aNormalAssertion->Parent()->Parent();
+ ProcessXORTermL(pNextChild,NewXorParent);
+ }
+ else
+ {
+ //SHOULDNT BE A CASE CAZ then we have XOR in some assertion
+ //It should always be in a POLICY tag
+ }
+ }
+
+
+ else if (localName.Compare(WSPolicy::KAndCompositeAssertion) == 0)
+ {
+ CSenElement* pNormChild = AddXorElementL(aNormalAssertion);
+
+ // aNormalAssertion =
+ ProcessANDTermL(pNextChild, pNormChild);
+ }
+
+
+ else if (localName.Compare(WSPolicy::KWsPolicy) == 0 )
+ {
+ TPtrC8 parentName = aNormalAssertion->LocalName();
+ if(parentName.Compare(WSPolicy::KXorCompositeAssertion) == 0)
+ {
+ CSenElement* pChildXor = AddXorElementL(aNormalAssertion);
+ CSenElement* pChildAnd = AddAndElementL(pChildXor);
+
+ }
+ else if(parentName.Compare(WSPolicy::KAndCompositeAssertion) == 0)
+ {
+ }
+ else if(parentName.Compare(WSPolicy::KWsPolicy) == 0)
+ {
+ CSenElement* pChildXor = AddXorElementL(aNormalAssertion);
+ CSenElement* pChildAnd = AddAndElementL(pChildXor);
+
+ }
+ else
+ {
+ CSenElement* pChildXor = AddXorElementL(aNormalAssertion);
+ CSenElement* pChildAnd = AddAndElementL(pChildXor);
+ }
+ }
+ else //its an Assertion
+ {
+ TPtrC8 parentName = assertionParent->LocalName();
+ //if parent is Policy -> add XOR and AND and then process
+ //assertion- >new parent for same level is AND
+
+ //if parent is XOR -> Add AND and then process assertion. at this level the parent will be AND
+ //if parent is AND just process assertion
+ if(IsOptionalL(pNextChild))
+ {
+ if(parentName.Compare(WSPolicy::KWsPolicy) == 0)
+ {
+ CSenElement* pXor = AddXorElementL(assertionParent);
+ CSenElement* pAnd = AddAndElementL(pXor);
+ // aNormalAssertion =
+ ProcessAssertionTermL(pNextChild, pAnd);
+ }
+ else if(parentName.Compare(WSPolicy::KAndCompositeAssertion) == 0)
+ {
+ CSenElement* parentNow = assertionParent;
+ assertionParent = assertionParent->Parent();
+ CSenElement* policyParent= assertionParent->Parent();
+ CSenElement* pXor = AddXorElementL(policyParent);
+ CSenElement* pAnd = AddAndElementL(pXor);
+ // aNormalAssertion =
+ ProcessAssertionTermL(pNextChild, pAnd);
+ assertionParent = parentNow;
+
+ }
+ else if(parentName.Compare(WSPolicy::KXorCompositeAssertion) == 0)
+ {
+
+ }
+ else
+ {
+ //probably error
+ }
+
+
+ }
+ else
+ {
+ if(parentName.Compare(WSPolicy::KWsPolicy) == 0)
+ {
+ CSenElement* pXor = AddXorElementL(assertionParent);
+ CSenElement* pAnd = AddAndElementL(pXor);
+ assertionParent = pAnd;
+ // assertionParent = ProcessAssertionTermL(pNextChild, pAnd);
+
+ }
+ else if(parentName.Compare(WSPolicy::KXorCompositeAssertion) == 0)
+ {
+
+ CSenElement* pXor = AddXorElementL(assertionParent);
+ CSenElement* pAnd = AddAndElementL(pXor);
+ // aNormalAssertion = ProcessAssertionTermL(pNextChild, pAnd);
+
+
+ }
+ else if(parentName.Compare(WSPolicy::KAndCompositeAssertion) == 0)
+ {
+
+ // aNormalAssertion = ProcessAssertionTermL(pNextChild, assertionParent);
+
+ }
+ else
+ {
+ CSenElement* pXor = AddXorElementL(assertionParent);
+ CSenElement* pAnd = AddAndElementL(pXor);
+ assertionParent = pAnd;
+ // aNormalAssertion = ProcessAssertionTermL(pNextChild, pAnd);
+ }
+
+ ProcessAssertionTermL(pNextChild, assertionParent);
+
+ }
+ }
+
+
+
+ i++;
+ }
+
+ return assertionParent;
+
+}
+CSenElement* CPolicyNormalizer::ProcessXORTermL(CSenElement* aAssertion, CSenElement* aNormalAssertion)
+{
+
+ CSenElement* pNormChild = AddXorElementL(aNormalAssertion);
+
+ RPointerArray<CSenElement>& children = aAssertion->ElementsL();
+ TInt childCount = children.Count();
+ TInt i = 0;
+
+ while (i < childCount)
+ {
+ CSenElement* pChild = children[i];
+
+ CSenElement* pNewChild = NULL;
+// CSenElement* newChild = NULL;
+
+ TPtrC8 childName = pChild->LocalName();
+
+ if(childName.Compare(WSPolicy::KAndCompositeAssertion) == 0)
+ {
+ //If AND element then take child of AND
+// CSenElement* newChild =
+ ProcessANDTermL(pChild, pNormChild);
+
+ }
+ else if (childName.Compare(WSPolicy::KXorCompositeAssertion) == 0)
+ {
+
+ }
+ else if(childName.Compare(WSPolicy::KWsPolicy) == 0)
+ {
+ pNewChild = AddAndElementL(pNormChild);
+ if(HasChildL(pChild) > 0)
+ ProcessPolicyTermL(pChild,pNewChild);
+ }
+ else
+ {
+ pNewChild = AddAndElementL(pNormChild);
+// newChild =
+ ProcessAssertionTermL(pChild, pNewChild);
+ //if Assertion then first we haveto add AND and then add Assertion
+ //(assertion will be done by AND too)
+ }
+
+ i++;
+ }
+
+
+ return pNormChild;
+
+}
+CSenElement* CPolicyNormalizer::ProcessANDTermL(CSenElement* aAssertion, CSenElement* aNormalAssertion)
+{
+ CSenElement* pNormChild = AddAndElementL(aNormalAssertion);
+
+ RPointerArray<CSenElement>& children = aAssertion->ElementsL();
+ TInt childCount = children.Count();
+// CSenElement* normalizedFinalChild = NULL;
+ TInt i=0;
+ while (i < childCount)
+ {
+ CSenElement* pChild = children[i];
+// CSenElement* newChild = NULL;
+
+ TPtrC8 childName = pChild->LocalName();
+
+ if(childName.Compare(WSPolicy::KAndCompositeAssertion) == 0)
+ {
+
+ }
+ else if (childName.Compare(WSPolicy::KXorCompositeAssertion) == 0)
+ {
+ //will be solved during collapsing
+
+ }
+ else if (childName.Compare(WSPolicy::KWsPolicy) == 0)
+ {
+ ProcessPolicyTermL(pChild,pNormChild);
+
+ }
+ else
+ {
+// normalizedFinalChild =
+ ProcessAssertionTermL(pChild, pNormChild);
+ }
+
+ i++;
+ }
+
+ return aNormalAssertion;
+}
+
+
+
+
+
+CSenElement* CPolicyNormalizer::ProcessLogicL(CSenElement* aTerm)
+{
+
+ //if sibling names are same as <ExactlyOne>
+ RPointerArray<CSenElement> matchingSiblings;
+ TInt matchingSiblingCount = 0;
+ if(aTerm->ElementsL(matchingSiblings, WSPolicy::KXorCompositeAssertion) == KErrNone)
+ matchingSiblingCount= matchingSiblings.Count();
+ if(matchingSiblingCount>1)
+ { //XOR elements should have AND elements in them else normalization error
+ //Find elements
+ CSenElement* firstSibling = matchingSiblings[0];
+
+ TInt i = 1;
+ while ( i < matchingSiblingCount)
+ {
+ CSenElement* nextSibling = matchingSiblings[i];
+ firstSibling = ProcessAndAndLogicL(firstSibling, nextSibling);
+
+ i++;
+ }
+ TInt j = 0;
+ while ( j < matchingSiblingCount)
+ {
+ CSenElement* removed = aTerm->RemoveElement(*matchingSiblings[j]);
+ if(removed)
+ delete removed;
+ j++;
+ }
+
+/**** aTerm->AddElementL(*firstSibling); */
+ }
+
+ RPointerArray<CSenElement>& children = aTerm->ElementsL();
+ TInt childCount = children.Count();
+
+ TInt i=0;
+
+
+ while (i < childCount)
+ {
+ CSenElement* pChild = children[i];
+
+ if(childCount == 1)
+ ProcessLogicL(pChild);
+
+ TPtrC8 childName = pChild->LocalName();
+ TPtrC8 parentName = aTerm->LocalName();
+
+
+ //if parent name and child name are same
+ if(childName.Compare(parentName) == 0)
+ {
+ if(childName.Compare(WSPolicy::KWsPolicy) == 0)
+ {
+
+ }
+ else if(childName.Compare(WSPolicy::KAndCompositeAssertion) == 0)
+ {
+
+ }
+ else if(childName.Compare(WSPolicy::KXorCompositeAssertion) == 0)
+ {
+ ProcessXorCollapseLogicL(aTerm,pChild);
+ continue;
+ }
+
+ }
+
+
+ i++;
+ }
+
+ matchingSiblings.Close();
+ return aTerm;
+}
+
+CSenElement* CPolicyNormalizer::ProcessXorCollapseLogicL(CSenElement* aParent, CSenElement* aChild)
+{
+ RPointerArray<CSenElement>& siblings = aParent->ElementsL();
+ RPointerArray<CSenElement>& collapsingChildren = aChild->ElementsL();
+
+ TInt childCount = collapsingChildren.Count();
+ TInt i=0;
+
+ RPointerArray<CSenElement> matchingSiblings;
+ TInt matchingSiblingCount = 0;
+ if(aParent->ElementsL(matchingSiblings, WSPolicy::KAndCompositeAssertion) == KErrNone)
+ matchingSiblingCount= matchingSiblings.Count();
+
+
+ while (i < childCount)
+ {
+ CSenElement* child = collapsingChildren[i];
+
+
+ for (TInt j = 0; j<matchingSiblingCount; j++)
+ {
+
+ RPointerArray<CSenElement>& siblingsChildren = matchingSiblings[j]->ElementsL();
+ TInt matchingSiblingChildrenCount= siblingsChildren.Count();
+
+ for (TInt k = 0; k<matchingSiblingChildrenCount; k++)
+ {
+ CSenElement* element = siblingsChildren[k];
+ child->AddElementL(*element);
+ // TPtrC8 name = detachedSibling->LocalName();
+
+ }
+
+
+ }
+ child->SetParent(aParent);
+ aParent->AddElementL(*child);
+
+
+ i++;
+ }
+
+ CSenElement* thisOne = aParent->RemoveElement(*aChild);
+ if(thisOne)
+ delete thisOne;
+
+ for (TInt j = 0; j<matchingSiblingCount; j++)
+ {
+ CSenElement* thisOneagain = aParent->RemoveElement(*matchingSiblings[j]);
+ if(thisOneagain)
+ delete thisOneagain;
+
+ }
+
+
+ return aParent;
+
+
+}
+CSenElement* CPolicyNormalizer::ProcessAssertionBranchingL(CSenElement* aPolicy)
+{
+
+ RPointerArray<CSenElement>& children = aPolicy->ElementsL();
+ TInt childCount = children.Count();
+
+ if(childCount == 0)
+ return aPolicy;
+
+ TInt i = 0;
+ while (i < childCount)
+ {
+ CSenElement* pChild = children[i];
+ TPtrC8 childName = pChild->LocalName();
+
+ if( childName.Compare(WSPolicy::KWsPolicy) == 0
+ || childName.Compare(WSPolicy::KAndCompositeAssertion) == 0
+ || childName.Compare(WSPolicy::KXorCompositeAssertion) == 0)
+ {
+ ProcessAssertionBranchingL(pChild);
+ }
+ else //Assertion
+ {
+ DuplicateAssertionBranchL(aPolicy , pChild);
+ }
+ i++;
+ }
+ return aPolicy;
+ }
+
+CSenElement* CPolicyNormalizer::DuplicateAssertionBranchL(CSenElement* /*aParent*/, CSenElement* aDuplicatingPolicy)
+{ //aDuplicatingPolicy is always an assertion
+//check if aDuplicatingPolicy have two assertions, if yes then divide the assertion in
+ // T W O separate assertions
+ //first check that if any of the two assertion themselve have
+
+ // if XOR have multiple ANDs then check if XOR parent is an Assertion.
+ // if yes then divide them in Two assertions.
+ TPtrC8 asseryName = aDuplicatingPolicy->LocalName();
+ TInt childCount = HasChildL(aDuplicatingPolicy);
+
+ if( childCount== 0) //There is NO CHILD NESTING in assertion
+ return aDuplicatingPolicy;
+ else if (childCount == 1) ////Assertion should always have only one <wsp:policy> element.
+ {
+ TBool deleted = EFalse;
+ CSenElement* assertionPolicyElement = aDuplicatingPolicy->Child(0); //policy element
+ TPtrC8 policyName = assertionPolicyElement->LocalName();
+ if(policyName.Compare(WSPolicy::KWsPolicy)== 0)
+ { //now we should have XOR and AND elements
+
+ CSenElement* assertionXORElement = assertionPolicyElement->Child(0); //XOR element
+ //there should be only one XOR element (in normalize mode)
+ TPtrC8 name1 = assertionXORElement->LocalName();
+ TInt AndElementCount = HasChildL(assertionXORElement);
+ //If it has only one AND child element then nuthing to do here but if more then one element
+ // then it means that assertion have nesting and should have a different branch.
+ if(AndElementCount == 0)
+ return aDuplicatingPolicy;
+ else if(AndElementCount == 1)
+ {
+ ProcessAssertionBranchingL(assertionXORElement->Child(0));
+ }
+ else if(AndElementCount > 1)
+ {
+ RPointerArray<CSenElement>& assertionXorChildren = assertionXORElement->ElementsL(); //AND elements
+ TInt i = 0;
+ while (i < AndElementCount)
+ {
+ //copy the root assertion to new tag
+ // Take out the replacing tag
+ // create two separate tag and replace them in the original and root copy tag
+
+ CSenXmlElement* AND = (CSenXmlElement*)assertionXorChildren[i];
+// ProcessAssertionBranchingL(AND);
+
+ CSenXmlElement* rootAssertion = (CSenXmlElement*)FindRootAssertionL(AND);
+ if (!IsChildOfElement(rootAssertion, AND))
+ {
+ i++;
+ continue;
+ }
+
+//create a duplicate tag,
+ //duplicating assertion
+ TPtrC8 assertionCopyName = rootAssertion->LocalName();
+ TPtrC8 assertionCopyNsUri = rootAssertion->NamespaceURI();
+ CSenXmlElement* XORParent = (CSenXmlElement*)rootAssertion->Parent();
+ CSenElement* parentsBrandNewRootAssertion =AddAndElementL(XORParent->Parent());
+
+ CSenElement& newDuplicateAssertion = parentsBrandNewRootAssertion->AddElementL(assertionCopyNsUri,assertionCopyName);
+
+//cut and paste the second AND to duplicate
+
+ newDuplicateAssertion.CopyFromL(*rootAssertion);
+
+ DeleteAsertionIndexL(aDuplicatingPolicy, &newDuplicateAssertion, i);
+ deleted = ETrue;
+// newDuplicateAssertion.SetParent(parentsBrandNewRootAssertion);
+ //parentsBrandNewRootAssertion->ReplaceElementL(newDuplicateAssertion);
+
+ //find from this new element the required assertion and then delete
+ // all of the optins from it except the current i+1 ALL element
+
+ i++;
+ }
+
+ if(deleted)
+ {
+ CSenElement* rootAssertion = FindRootAssertionL(aDuplicatingPolicy);
+ CSenElement* AND = rootAssertion->Parent();
+ CSenElement* XOR = AND->Parent();
+ CSenElement* thisOne = XOR->RemoveElement(*AND);
+ if(thisOne)
+ iOrphanElements.Append(thisOne);
+// delete thisOne; //P DuplicateAssertionBranch A T H E T I C H A C K
+ //now we have solved the first level nesting
+ //our original policy is changed so now use the original policy and solve it again
+ CSenElement* documentRoot = (CSenElement*)&XOR->Root();
+ ProcessAssertionBranchingL(documentRoot);
+
+ }
+
+
+ }
+ }
+ }
+ else if(childCount > 1)
+ {
+ //this count is always one because its a child wsp:policy element, policy element
+ //could have multiple XOR elements . If it comes here something is W R O N G
+
+ }
+ //here is the nesting problem. the assertion policy should have only one
+ // Alternative = <XOR><AND>< --assertion-- ></AND></XOR>
+ // NO TWO XORs are allowed here
+ return aDuplicatingPolicy;
+}
+CSenElement* CPolicyNormalizer::DeleteAsertionIndexL(CSenElement* aAssertion, CSenElement* anewAssertion, TInt aIndx)
+{
+ TPtrC8 name = aAssertion->LocalName();
+ TPtrC8 nsUri = aAssertion->NamespaceURI();
+ TInt i = 0;
+
+ RPointerArray<CSenElement>& assertionChildren = anewAssertion->ElementsL();
+ TInt newAssertionChildCount = assertionChildren.Count();
+
+ if(newAssertionChildCount == 0)
+ return anewAssertion;
+
+ TPtrC8 namee = anewAssertion->LocalName();
+ if (name.Compare(anewAssertion->LocalName())== 0)
+ { //delete children from this assertion except index child
+ CSenXmlElement* PolicyElement = (CSenXmlElement*)anewAssertion->Child(0);
+ CSenXmlElement* XORElement = (CSenXmlElement*)PolicyElement->Child(0);
+ RPointerArray<CSenElement>& XorChildren = XORElement->ElementsL();
+ TInt XORChildrenCount = XorChildren.Count();
+
+ for (TInt k = 0; k <XORChildrenCount; k++)
+ {
+ if(k == aIndx)
+ {
+
+ }
+ else
+ {
+ CSenElement* newElement = XORElement->RemoveElement(*XorChildren[XORChildrenCount-1-k]);
+ if(newElement)
+ {
+ delete newElement;
+ // break;
+ }
+
+ }
+
+ }
+ return anewAssertion;
+ }
+
+ while (i < newAssertionChildCount)
+ {
+
+ DeleteAsertionIndexL(aAssertion, assertionChildren[i], aIndx);
+ i++;
+ }
+
+ return anewAssertion;
+}
+CSenElement* CPolicyNormalizer::FindRootAssertionL(CSenElement* aElement)
+{
+
+ CSenElement* rootAssertionTag = NULL;
+
+ CSenElement* documentRoot = (CSenElement*)&aElement->Root();
+ CSenElement* doumentXOR = documentRoot->Child(0); //cant be more then one :p
+
+ //find first assertion here
+ RPointerArray<CSenElement>& children = doumentXOR->ElementsL(); //AND elements
+ TInt childCount = children.Count();
+
+ if(childCount == 0) //something invalid with document
+ return aElement;
+
+ else if (childCount > 0) //onyl one AND element, Next child should be root Assertion
+ {
+ TInt i = 0;
+ while (i < childCount)
+ {
+ CSenElement* andTag = children[i];
+ TInt andAssertions = HasChildL(andTag);
+
+ if(andAssertions == 0)
+ return aElement;
+ else if(andAssertions == 1)
+ {
+ TBool isChild = IsChildOfElement(andTag->Child(0), aElement);
+ if(isChild)
+ return andTag->Child(0);
+ }
+ else if (andAssertions > 1)
+ {
+ RPointerArray<CSenElement>& rootAssertions = andTag->ElementsL(); //AND elements
+ TInt j = 0;
+ while (j < andAssertions)
+ {
+
+ TBool isChild = IsChildOfElement(rootAssertions[j], aElement);
+
+ if(isChild)
+ {
+ rootAssertionTag = rootAssertions[j];
+ break;
+ }
+
+ j++;
+ }
+ }
+ i++;
+ }
+
+
+ }
+ else if (childCount > 1)
+ {
+
+
+ }
+
+ return rootAssertionTag;
+
+}
+TBool CPolicyNormalizer::IsChildOfElement(CSenElement* aParent, CSenElement* aChild)
+{ //aParent and child botth are assertions
+
+ CSenElement* rootChildAssertionTag = aChild; //->Parent();
+ TPtrC8 nqame1 = aParent->LocalName();
+ while (true)
+ {
+
+ if(rootChildAssertionTag)
+ {
+
+ TPtrC8 nqame2 = rootChildAssertionTag->LocalName();
+
+ if(rootChildAssertionTag == aParent)
+ {
+ return ETrue;
+
+ }
+ }
+ else
+ {
+ return EFalse;
+ }
+ rootChildAssertionTag = rootChildAssertionTag->Parent();
+ }
+}
+CSenElement* CPolicyNormalizer::ProcessAndCollapseLogic(CSenElement* aParent, CSenElement* /*aChild*/)
+{
+ return aParent;
+}
+
+CSenElement* CPolicyNormalizer::ProcessAndAndLogicL(CSenElement* aFirstTerm, CSenElement* aSecondTerm )
+{
+ //Two XOR XOR parameters are given which have same parent and have AND child elements,
+ //The AND child elements will be resolved according to Ditributive law
+ //takes all child Assertion elements from SecondTerm and put them in first term
+
+
+ RPointerArray<CSenElement> matchingSiblingsFirst;
+ CleanupClosePushL(matchingSiblingsFirst);
+
+ if(aFirstTerm->ElementsL(matchingSiblingsFirst, WSPolicy::KAndCompositeAssertion) == KErrNone
+ || aFirstTerm->ElementsL(matchingSiblingsFirst, WSPolicy::KXorCompositeAssertion) == KErrNone
+ || aFirstTerm->ElementsL(matchingSiblingsFirst, WSPolicy::KWsPolicy) == KErrNone
+ || aSecondTerm->ElementsL(matchingSiblingsFirst, WSPolicy::KAndCompositeAssertion) == KErrNone
+ || aSecondTerm->ElementsL(matchingSiblingsFirst, WSPolicy::KXorCompositeAssertion) == KErrNone
+ || aSecondTerm->ElementsL(matchingSiblingsFirst, WSPolicy::KWsPolicy) == KErrNone)
+
+
+
+ { // they are NOT the last children so first go deep to last assertion and then process that assertion
+ ProcessLogicL(aFirstTerm);
+ ProcessLogicL(aSecondTerm);
+ }
+ CleanupStack::PopAndDestroy();//matchingSiblingsFirst
+
+// else // they are the last children
+
+
+ RPointerArray<CSenElement>& siblings = aFirstTerm->ElementsL();
+ RPointerArray<CSenElement>& collapsingChildren = aSecondTerm->ElementsL();
+
+
+ TInt siblingsCount = siblings.Count();
+ TInt childCount = collapsingChildren.Count();
+
+ if(siblingsCount == 0)
+ return aFirstTerm;
+ else if (childCount == 0)
+ return aSecondTerm;
+
+ TInt i=0;
+ TInt j=0;
+
+ CSenElement* collpasingElement = NULL;
+ CSenElement* returningElement = NULL;
+ if(siblingsCount < childCount)
+ {
+ CSenElement& distributiveElement = aFirstTerm->Parent()->AddElementL(WSPolicy::KWsPolicyNsUri,WSPolicy::KXorCompositeAssertion);;
+// distributiveElement = CSenXmlElement::NewL(WSPolicy::KWsPolicyNsUri,WSPolicy::KXorCompositeAssertion);
+// aFirstTerm->Parent()->AddElementL(*distributiveElement);
+// distributiveElement->SetParent(aFirstTerm->Parent());
+
+ while(j < childCount)
+ { //chnage logic for <ALL/>
+/*
+
+<XOR>
+ <AND>
+ <!--assertion1-->
+ </AND>
+ <AND/>
+</XOR>
+<XOR>
+ <AND>
+ <!--assertion3-->
+ </AND>
+ <AND>
+ <!--assertion4-->
+ </AND>
+
+</XOR>
+
+1.make assertion1 assertion 3
+2. make assertion 2 assertion 3
+3. Replace <AND/> with all the assertions from second <XOR> i.e.
+with
+ <AND>
+ <!--assertion3-->
+ </AND>
+ <AND>
+ <!--assertion4-->
+ </AND>
+*/
+ CSenElement* newParentElement = collapsingChildren[j];
+
+ TBool EmptyAndElement = EFalse;
+ if (HasChildL(newParentElement) < 1)
+ {
+ EmptyAndElement = ETrue;
+ }
+
+ while(i < siblingsCount)
+ {
+ collpasingElement = siblings[i];
+
+ RPointerArray<CSenElement>& collpasEleAssertion = collpasingElement->ElementsL();
+ TInt countt = collpasEleAssertion.Count();
+
+ if(EmptyAndElement) //copy all elements from here to new parent
+ {
+
+ CSenElement& ele = distributiveElement.AddElementL(collpasingElement->NamespaceURI(), collpasingElement->LocalName());
+ ele.CopyFromL(*collpasingElement);
+ }
+// else if(collpasingElement->Child(0))
+// newParentElement->AddElementL(*collpasingElement->Child(0));
+ else
+ { //This is an empty <ALL /> element so use distributive law to resolve it
+
+ CSenElement* AndElement = AddAndElementL(&distributiveElement);
+ //copy here all elements from first AND element and 2nd AND element
+
+ RPointerArray<CSenElement>& ParentChildren = newParentElement->ElementsL();
+ TInt countHere = ParentChildren.Count();
+ for (TInt k = 0; k < countHere; k++)
+ {
+ CSenElement* pkChild = ParentChildren[k];
+ CSenElement& here = AndElement->AddElementL(pkChild->NamespaceURI(), pkChild->LocalName());
+ here.CopyFromL(*pkChild);
+ }
+ for(TInt l = 0; l < countt; l++)
+ {
+ CSenElement* paChild = collpasEleAssertion[l];
+ CSenElement& hereAgain = AndElement->AddElementL(paChild->NamespaceURI(), paChild->LocalName());
+ hereAgain.CopyFromL(*paChild);
+
+ }
+
+ }
+ i++;
+ }
+ i = 0;
+ j++;
+ }
+ returningElement = &distributiveElement;
+ CSenElement* parentElement = aFirstTerm->Parent();
+// parentElement->RemoveElement(*aFirstTerm);
+
+ }
+ else
+ {
+ CSenElement& distributiveElement = aFirstTerm->Parent()->AddElementL(WSPolicy::KWsPolicyNsUri,WSPolicy::KXorCompositeAssertion);;
+// distributiveElement = CSenXmlElement::NewL(WSPolicy::KWsPolicyNsUri,WSPolicy::KXorCompositeAssertion);
+// aFirstTerm->Parent()->AddElementL(*distributiveElement);
+// distributiveElement->SetParent(aFirstTerm->Parent());
+ while(j < siblingsCount)
+ {
+ CSenElement* newParentElement = siblings[j]; //AND element
+
+ TBool EmptyAndElement = EFalse;
+ if (HasChildL(newParentElement) < 1)
+ {
+ EmptyAndElement = ETrue;
+ }
+
+
+ while(i < childCount)
+ {
+ collpasingElement = collapsingChildren[i]; //AND element
+
+ RPointerArray<CSenElement>& collpasEleAssertion = collpasingElement->ElementsL(); // AND element Assertions
+ TInt countt = collpasEleAssertion.Count();
+
+ if(EmptyAndElement) //copy all elements from here to new parent
+ {
+ CSenElement& ele = distributiveElement.AddElementL(collpasingElement->NamespaceURI(), collpasingElement->LocalName());
+ ele.CopyFromL(*collpasingElement);
+ }
+// else if(countt == 1) //If AND has only one assertion
+// newParentElement->AddElementL(*collpasingElement->Child(0));
+ else //if(countt > 1)
+ { //Distributive Law
+
+ CSenElement* AndElement = AddAndElementL(&distributiveElement);
+ //copy here all elements from first AND element and 2nd AND element
+
+ RPointerArray<CSenElement>& ParentChildren = newParentElement->ElementsL();
+ TInt countHere = ParentChildren.Count();
+ for (TInt k = 0; k < countHere; k++)
+ {
+ CSenElement* pkChild = ParentChildren[k];
+ CSenElement& here = AndElement->AddElementL(pkChild->NamespaceURI(), pkChild->LocalName());
+ here.CopyFromL(*pkChild);
+ }
+ for(TInt l = 0; l < countt; l++)
+ {
+ CSenElement* paChild = collpasEleAssertion[l];
+ CSenElement& hereAgain = AndElement->AddElementL(paChild->NamespaceURI(), paChild->LocalName());
+ hereAgain.CopyFromL(*paChild);
+ }
+
+ }
+ i++;
+ }
+ i = 0;
+ j++;
+ }
+ returningElement = &distributiveElement; //; aFirstTerm;
+ CSenElement* parentElement = aSecondTerm->Parent();
+ }
+
+ return returningElement;
+
+}
+
+TInt CPolicyNormalizer::HasChildL(CSenElement* aTerm)
+{
+ RPointerArray<CSenElement>& children = aTerm->ElementsL();
+
+ TInt childCount = children.Count();
+ return childCount;
+
+}
+
+CSenElement* CPolicyNormalizer::AddAndElementL(CSenElement* aAssertion)
+{
+
+ CSenElement& newElement = aAssertion->AddElementL(WSPolicy::KWsPolicyNsUri,
+ WSPolicy::KAndCompositeAssertion);
+ return &newElement;
+
+}
+
+CSenElement* CPolicyNormalizer::AddXorElementL(CSenElement* aAssertion)
+{
+ CSenElement& newElement = aAssertion->AddElementL(WSPolicy::KWsPolicyNsUri,
+ WSPolicy::KXorCompositeAssertion);
+ return &newElement;
+
+}
+
+CSenElement* CPolicyNormalizer::AddPolicyElementL(CSenElement* aAssertion)
+{
+ CSenElement& newElement = aAssertion->AddElementL(WSPolicy::KWsPolicyNsUri,
+ WSPolicy::KWsPolicy);
+ return &newElement;
+}
+
+
+
+TBool CPolicyNormalizer::ValidateElementNsL(CSenElement* aAssertion)
+{
+
+ CSenElement& element = AsElement();
+ RPointerArray<CSenNamespace>& namespaces = element.NamespacesL();
+
+ if(aAssertion->NamespaceURI().Length() < 1 )
+ {
+
+ TPtrC8 elementName = aAssertion->LocalName();
+ TInt location = elementName.Find(KColon);
+
+ if (location)
+ {
+ TPtrC8 nsPrefix = elementName.Left(location);
+
+ CSenNamespace* ns = NULL;
+ TInt count = namespaces.Count();
+ for (TInt i=0; i < count; i++)
+ {
+ ns = (namespaces)[i];
+ if(ns->Prefix().Compare(nsPrefix) == 0)
+ {
+ aAssertion->SetNamespaceL(ns->Prefix(),ns->URI());
+ return ETrue;
+ }
+ }
+ }
+ }
+ return EFalse;
+}
+
+
+TBool CPolicyNormalizer::CopySenElementWithoutOptionL(CSenElement* aSource,CSenElement* aDestination)
+{
+
+ TPtrC8 sourceContent = aSource->Content();
+ TBool isTrue = EFalse;
+ if (sourceContent.Length() > 0)
+ {
+ aDestination->SetContentL(sourceContent);
+
+ }
+
+ RPointerArray<CSenBaseAttribute> sourceAttributes = aSource->AttributesL();
+ if (sourceAttributes.Count() > 0)
+ {
+ for (TInt i=0;i<sourceAttributes.Count(); i++)
+ {
+ CSenBaseAttribute* pBaseAttribute = sourceAttributes[i];
+ if(pBaseAttribute->Name().Compare(WSPolicy::KWspOptinal) == 0)
+ {
+ if(pBaseAttribute->Value().Compare(WSPolicy::KWspOptinalTrue) == 0)
+ isTrue = ETrue;
+ }
+
+ else
+ aDestination->AddAttributeL(pBaseAttribute->Name(),pBaseAttribute->Value());
+
+ }
+ }
+// sourceAttributes.Close();
+ return isTrue;
+}
+
+CSenElement* CPolicyNormalizer::CopySenElementL(CSenElement* aSource, CSenElement* aDestination)
+{
+ TPtrC8 sourceContent = aSource->Content();
+ if (sourceContent.Length() > 0)
+ {
+ aDestination->SetContentL(sourceContent);
+
+ }
+ aDestination->SetNamespaceL(aSource->NsPrefix(), aSource->NamespaceURI());
+
+ RPointerArray<CSenBaseAttribute> sourceAttributes = aSource->AttributesL();
+ if (sourceAttributes.Count() > 0)
+ {
+ for (TInt i=0;i<sourceAttributes.Count(); i++)
+ {
+ CSenBaseAttribute* pBaseAttribute = sourceAttributes[i];
+
+ aDestination->AddAttributeL(pBaseAttribute->Name(),
+ pBaseAttribute->Value());
+
+ }
+ }
+// sourceAttributes.Close();
+ return aDestination;
+}
+
+void CPolicyNormalizer::ReadFileL( TFileName aPath )
+ {
+ RFs fss;
+ User::LeaveIfError(fss.Connect());
+ CleanupClosePushL(fss);
+
+ if(iPath)
+ {
+ delete iPath;
+ iPath = NULL;
+ }
+
+ iPath = aPath.AllocL();
+
+ TFileName iFileName(aPath);
+ RFile xmlFile;
+ TInt err = xmlFile.Open(fss , iFileName, EFileRead );
+
+ if(err == KErrNone)
+ {
+ TInt size;
+ xmlFile.Size(size);
+
+ HBufC8 *iBuf=HBufC8::NewL(size);
+
+ TPtr8 buf8ptr(iBuf->Des());
+ xmlFile.Read(buf8ptr,size);
+ xmlFile.Close();
+
+ TInt leaveCode(KErrNone);
+ TRAP leaveCode, ParseL(buf8ptr) );
+ leaveCode = 0; // not used currently
+ delete iBuf;
+ iBuf = NULL;
+ }
+ CleanupStack::PopAndDestroy(1); // fss
+ }
+
+TInt CPolicyNormalizer::ReadL(TDesC8& aXmlDesc)
+ {
+ TInt err (KErrNone);
+ TInt size = aXmlDesc.Length();
+ if(size > 0)
+ {
+ HBufC8 *pBuf= aXmlDesc.AllocL();
+ CleanupStack::PushL(pBuf);
+ TPtr8 buf8ptr(pBuf->Des());
+
+ TRAP (err, ParseL(buf8ptr));
+
+ CleanupStack::PopAndDestroy(pBuf);
+ }
+ return err;
+ }
+
+void CPolicyNormalizer::WriteAllL(CSenElement* /*aXml*/)
+{
+ RFs fss;
+ User::LeaveIfError(fss.Connect());
+ CleanupClosePushL(fss);
+
+ TBuf<255> file;
+ _LIT( KFileName, "c:\\logs\\normalizer%d.xml");
+ file.Format(KFileName, count);
+ count++;
+ TPtrC OutputFile(file);
+
+ TBuf<256> tempp(KOutPath);
+// tempp.Insert(tempp.Length() , iPath->Des());
+
+// TFileName iFileName(tempp);
+ RFile xmlFile;
+ xmlFile.Replace(fss , OutputFile, EFileWrite );
+ HBufC8* temp = iNewPolicy->AsXmlL();
+ xmlFile.Write(temp->Des());
+ xmlFile.Close();
+ delete temp;
+
+ CleanupStack::PopAndDestroy(1); // fss
+
+}
+void CPolicyNormalizer::WriteL(CSenElement* aXml)
+{
+ RFs fss;
+ User::LeaveIfError(fss.Connect());
+ CleanupClosePushL(fss);
+
+ TBuf<255> file;
+ _LIT( KFileName, "c:\\logs\\normalizer%d.xml");
+ file.Format(KFileName, count);
+ count++;
+ TPtrC OutputFile(file);
+
+ TBuf<256> tempp(KOutPath);
+// tempp.Insert(tempp.Length() , iPath->Des());
+
+// TFileName iFileName(tempp);
+ RFile xmlFile;
+ xmlFile.Replace(fss , OutputFile, EFileWrite );
+ HBufC8* temp = aXml->AsXmlL();
+ xmlFile.Write(temp->Des());
+ xmlFile.Close();
+ delete temp;
+
+ CleanupStack::PopAndDestroy(1); // fss
+
+}
+
+// End of file