Пример #1
0
        public override void OutAStructDecl(AStructDecl node)
        {
            //Insert init in each constructor
            AThisLvalue    thisLvalue    = new AThisLvalue(new TThis("this"));
            ALvalueExp     thisExp       = new ALvalueExp(thisLvalue);
            APointerLvalue pointerLvalue = new APointerLvalue(new TStar("*"), thisExp);

            ANamedType namedType = new ANamedType(new TIdentifier(node.GetName().Text), null);

            data.StructTypeLinks[namedType] = node;
            data.LvalueTypes[thisLvalue]    =
                data.ExpTypes[thisExp]      = new APointerType(new TStar("*"), namedType);
            data.LvalueTypes[pointerLvalue] = namedType;


            foreach (AConstructorDecl constructor in node.GetLocals().OfType <ADeclLocalDecl>().Select(decl => decl.GetDecl()).OfType <AConstructorDecl>())
            {
                AABlock block = new AABlock(new ArrayList(), new TRBrace("}"));
                MakeAssignments(block, namedType, pointerLvalue, false);

                ((AABlock)constructor.GetBlock()).GetStatements().Insert(0, new ABlockStm(new TLBrace("{"), block));
            }

            base.OutAStructDecl(node);
        }
Пример #2
0
        public override void CaseADelegateExp(ADelegateExp node)
        {
            /* Replace delegate<Type>(method)
             * With
             *
             * "method"
             *
             * or
             *
             * "method:reciever"
             */
            AMethodDecl    method = finalTrans.data.DelegateCreationMethod[node];
            string         d      = GetName(method);
            PExp           replacer;
            APointerLvalue reciever = finalTrans.data.DelegateRecieveres[node];

            if (reciever != null)
            {
                d += ":";
                AStringConstExp leftSide = new AStringConstExp(new TStringLiteral("\"" + d + "\""));
                replacer = new ABinopExp(leftSide, new APlusBinop(new TPlus("+")), reciever.GetBase());
                finalTrans.data.ExpTypes[leftSide]     =
                    finalTrans.data.ExpTypes[replacer] = new ANamedType(new TIdentifier("string"), null);

                if (Util.IsIntPointer(reciever, data.LvalueTypes[reciever], data))
                {
                    ASimpleInvokeExp intToStringInvoke = new ASimpleInvokeExp(new TIdentifier("IntToString"),
                                                                              new ArrayList()
                    {
                        ((ABinopExp)replacer).GetRight()
                    });
                    ((ABinopExp)replacer).SetRight(intToStringInvoke);

                    finalTrans.data.SimpleMethodLinks[intToStringInvoke] =
                        data.Libraries.Methods.First(m => m.GetName().Text == intToStringInvoke.GetName().Text);
                    data.ExpTypes[intToStringInvoke] = new ANamedType(new TIdentifier("string"), null);
                }
            }
            else
            {
                replacer = new AStringConstExp(new TStringLiteral("\"" + d + "\""));
                finalTrans.data.ExpTypes[replacer] = new ANamedType(new TIdentifier("string"), null);
            }
            MoveMethodDeclsOut mover = new MoveMethodDeclsOut("delegateVar", finalTrans.data);

            node.Apply(mover);
            node.ReplaceBy(replacer);
            foreach (PStm stm in mover.NewStatements)
            {
                stm.Apply(this);
            }
        }
Пример #3
0
        public override void OutAPointerMultiLvalue(APointerMultiLvalue node)
        {
            ALvalueExp     lvalueExp;
            APointerLvalue pointerLvalue = new APointerLvalue((TStar)node.GetTokens()[0], node.GetBase());

            while (node.GetTokens().Count > 0)
            {
                lvalueExp     = new ALvalueExp(pointerLvalue);
                pointerLvalue = new APointerLvalue((TStar)node.GetTokens()[0], lvalueExp);
            }

            node.ReplaceBy(pointerLvalue);
            pointerLvalue.Apply(this);
        }
Пример #4
0
 public override void OutAPointerLvalue(APointerLvalue node)
 {
     data.LvalueTypes[node] = ((APointerType)data.ExpTypes[node.GetBase()]).GetType();
 }
Пример #5
0
 bool IsConstant(PLvalue lvalue)
 {
     if (lvalue is ALocalLvalue)
     {
         ALocalLvalue aLvalue = (ALocalLvalue)lvalue;
         AALocalDecl  decl    = data.LocalLinks[aLvalue];
         if (decl == initialLocalDecl)
         {
             return(false);
         }
         return(decl.GetConst() != null && IsConstant(decl.GetInit()));
     }
     if (lvalue is AFieldLvalue)
     {
         AFieldLvalue aLvalue = (AFieldLvalue)lvalue;
         AFieldDecl   decl    = data.FieldLinks[aLvalue];
         if (decl == initialFieldDecl)
         {
             return(false);
         }
         return(decl.GetConst() != null && IsConstant(decl.GetInit()));
     }
     if (lvalue is APropertyLvalue)
     {
         return(false);
     }
     if (lvalue is ANamespaceLvalue)
     {
         return(true);
     }
     if (lvalue is AStructFieldLvalue)
     {
         AStructFieldLvalue aLvalue = (AStructFieldLvalue)lvalue;
         AALocalDecl        decl    = data.StructMethodFieldLinks[aLvalue];
         if (decl == initialLocalDecl)
         {
             return(false);
         }
         return(decl.GetConst() != null && IsConstant(decl.GetInit()));
     }
     if (lvalue is AStructLvalue)
     {
         AStructLvalue aLvalue = (AStructLvalue)lvalue;
         AALocalDecl   decl    = data.StructFieldLinks[aLvalue];
         if (decl == initialLocalDecl)
         {
             return(false);
         }
         return(decl.GetConst() != null && IsConstant(decl.GetInit()));
     }
     if (lvalue is AArrayLvalue)
     {
         AArrayLvalue aLvalue = (AArrayLvalue)lvalue;
         return(IsConstant(aLvalue.GetIndex()) && IsConstant(aLvalue.GetBase()));
     }
     if (lvalue is APointerLvalue)
     {
         APointerLvalue aLvalue = (APointerLvalue)lvalue;
         return(IsConstant(aLvalue.GetBase()));
     }
     if (lvalue is APArrayLengthLvalue)
     {
         APArrayLengthLvalue aLvalue = (APArrayLengthLvalue)lvalue;
         return(data.ExpTypes[aLvalue.GetBase()] is AArrayTempType);
     }
     if (lvalue is AThisLvalue)
     {
         return(false);
     }
     if (lvalue is AValueLvalue)
     {
         return(false);
     }
     throw new Exception("Unexpected lvalue. Got " + lvalue);
 }
Пример #6
0
            /*
             * Apply after assignement fixup
             * Assume no i++
             *
             * Convert usages to method invocations.
             */

            public static void Parse(FinalTransformations finalTrans)
            {
                SharedData data = finalTrans.data;

                foreach (KeyValuePair <APropertyLvalue, APropertyDecl> pair in data.PropertyLinks)
                {
                    APropertyLvalue lvalue   = pair.Key;
                    APropertyDecl   property = pair.Value;

                    if (Util.GetAncestor <AAProgram>(lvalue) == null)
                    {
                        continue;
                    }

                    if (lvalue.Parent() is AAssignmentExp)
                    {
                        AAssignmentExp   assignment = (AAssignmentExp)lvalue.Parent();
                        ASimpleInvokeExp invoke     =
                            new ASimpleInvokeExp(
                                new TIdentifier("Set" + property.GetName().Text, lvalue.GetName().Line,
                                                lvalue.GetName().Pos), new ArrayList()
                        {
                            assignment.GetExp()
                        });
                        assignment.ReplaceBy(invoke);
                        data.SimpleMethodLinks[invoke] = data.Setters[property];
                        data.ExpTypes[invoke]          = new AVoidType(new TVoid("void"));
                    }
                    else
                    {
                        ALvalueExp       exp    = (ALvalueExp)lvalue.Parent();
                        ASimpleInvokeExp invoke =
                            new ASimpleInvokeExp(
                                new TIdentifier("Get" + property.GetName().Text, lvalue.GetName().Line,
                                                lvalue.GetName().Pos), new ArrayList()
                        {
                        });
                        exp.ReplaceBy(invoke);
                        data.SimpleMethodLinks[invoke] = data.Getters[property];
                        data.ExpTypes[invoke]          = property.GetType();
                    }
                }
                foreach (KeyValuePair <AStructLvalue, APropertyDecl> pair in data.StructPropertyLinks)
                {
                    AStructLvalue   lvalue         = pair.Key;
                    APropertyDecl   property       = pair.Value;
                    AEnrichmentDecl enrichmentDecl = null;
                    AStructDecl     structDecl     = null;
                    if (data.EnrichmentTypeLinks.ContainsKey(data.ExpTypes[lvalue.GetReceiver()]))
                    {
                        enrichmentDecl = data.EnrichmentTypeLinks[data.ExpTypes[lvalue.GetReceiver()]];
                    }
                    if (enrichmentDecl == null)
                    {
                        structDecl = data.StructTypeLinks[(ANamedType)data.ExpTypes[lvalue.GetReceiver()]];
                    }

                    if (Util.GetAncestor <AAProgram>(lvalue) == null)
                    {
                        continue;
                    }

                    PExp structArg;
                    if (structDecl == null || structDecl.GetClassToken() == null)
                    {
                        structArg = lvalue.GetReceiver();
                    }
                    else
                    {
                        //Send pointer
                        ALvalueExp     lvalueExp    = (ALvalueExp)lvalue.GetReceiver();
                        APointerLvalue pointerValue = (APointerLvalue)lvalueExp.GetLvalue();
                        structArg = pointerValue.GetBase();
                    }

                    if (lvalue.Parent() is AAssignmentExp)
                    {
                        AAssignmentExp   assignment = (AAssignmentExp)lvalue.Parent();
                        ASimpleInvokeExp invoke     =
                            new ASimpleInvokeExp(
                                new TIdentifier("Set" + property.GetName().Text, lvalue.GetName().Line,
                                                lvalue.GetName().Pos), new ArrayList()
                        {
                            assignment.GetExp(), structArg
                        });
                        assignment.ReplaceBy(invoke);
                        data.SimpleMethodLinks[invoke] = data.Setters[property];
                        data.ExpTypes[invoke]          = new AVoidType(new TVoid("void"));
                    }
                    else
                    {
                        ALvalueExp       exp    = (ALvalueExp)lvalue.Parent();
                        ASimpleInvokeExp invoke =
                            new ASimpleInvokeExp(
                                new TIdentifier("Get" + property.GetName().Text, lvalue.GetName().Line,
                                                lvalue.GetName().Pos), new ArrayList()
                        {
                            structArg
                        });
                        exp.ReplaceBy(invoke);
                        data.SimpleMethodLinks[invoke] = data.Getters[property];
                        data.ExpTypes[invoke]          = property.GetType();
                    }
                }
                foreach (KeyValuePair <AArrayLvalue, Util.Pair <APropertyDecl, bool> > pair in data.ArrayPropertyLinks)
                {
                    AArrayLvalue    lvalue         = pair.Key;
                    APropertyDecl   property       = pair.Value.First;
                    bool            implicitMatch  = pair.Value.Second;
                    AEnrichmentDecl enrichmentDecl = null;
                    AStructDecl     structDecl     = null;

                    if (OldEnrichmentParents.ContainsKey(property))
                    {
                        enrichmentDecl = OldEnrichmentParents[property];
                    }
                    else
                    {
                        structDecl = OldStructParents[property];
                    }
                    if (Util.GetAncestor <AAProgram>(lvalue) == null)
                    {
                        continue;
                    }

                    PExp structArg;
                    if (structDecl == null || structDecl.GetClassToken() == null)
                    {
                        structArg = lvalue.GetBase();
                    }
                    else
                    {
                        //Send pointer
                        if (implicitMatch)
                        {
                            structArg = lvalue.GetBase();
                        }
                        else
                        {
                            ALvalueExp     lvalueExp    = (ALvalueExp)lvalue.GetBase();
                            APointerLvalue pointerValue = (APointerLvalue)lvalueExp.GetLvalue();
                            structArg = pointerValue.GetBase();
                        }
                    }

                    /*  if (!(structArg is ALvalueExp &&
                     *    (((ALvalueExp)structArg).GetLvalue() is ALocalLvalue || ((ALvalueExp)structArg).GetLvalue() is AFieldLvalue ||
                     *    ((ALvalueExp)structArg).GetLvalue() is AStructLvalue || ((ALvalueExp)structArg).GetLvalue() is AStructFieldLvalue))
                     * {
                     *    //Make new local
                     *    AALocalDecl decl = new AALocalDecl(new APublicVisibilityModifier(), null, null, null, null,
                     *                                       Util.MakeClone(data.ExpTypes[structArg], data),
                     *                                       new TIdentifier("propertyVar"), structArg);
                     *    ALocalLvalue declRef = new ALocalLvalue(new TIdentifier("propertyVar"));
                     *    structArg = new ALvalueExp(declRef);
                     *    PStm stm = Util.GetAncestor<PStm>(lvalue);
                     * }*/

                    if (lvalue.Parent() is AAssignmentExp)
                    {
                        AAssignmentExp   assignment = (AAssignmentExp)lvalue.Parent();
                        ASimpleInvokeExp invoke     =
                            new ASimpleInvokeExp(
                                new TIdentifier("SetThis", lvalue.GetToken().Line,
                                                lvalue.GetToken().Pos), new ArrayList()
                        {
                            lvalue.GetIndex(), assignment.GetExp(), structArg
                        });
                        assignment.ReplaceBy(invoke);
                        data.SimpleMethodLinks[invoke] = data.Setters[property];
                        data.ExpTypes[invoke]          = new AVoidType(new TVoid("void"));
                    }
                    else
                    {
                        ALvalueExp       exp    = (ALvalueExp)lvalue.Parent();
                        ASimpleInvokeExp invoke =
                            new ASimpleInvokeExp(
                                new TIdentifier("GetThis", lvalue.GetToken().Line,
                                                lvalue.GetToken().Pos), new ArrayList()
                        {
                            lvalue.GetIndex(), structArg
                        });
                        exp.ReplaceBy(invoke);
                        data.SimpleMethodLinks[invoke] = data.Getters[property];
                        data.ExpTypes[invoke]          = property.GetType();
                    }
                }
            }
        public override void CaseANonstaticInvokeExp(ANonstaticInvokeExp node)
        {
            PExp  reciever = node.GetReceiver();
            PType type     = finalTrans.data.ExpTypes[reciever];

            //If the reciever is not a var, put it in a new var.
            if (!(reciever is ALvalueExp))
            {
                AALocalDecl  localDecl   = new AALocalDecl(new APublicVisibilityModifier(), null, null, null, null, Util.MakeClone(type, data), new TIdentifier("nonstaticInvokeVar"), reciever);
                ALocalLvalue localRef    = new ALocalLvalue(new TIdentifier("nonstaticInvokeVar"));
                ALvalueExp   localRefExp = new ALvalueExp(localRef);
                node.SetReceiver(localRefExp);
                PStm    pStm   = Util.GetAncestor <PStm>(node);
                AABlock pBlock = (AABlock)pStm.Parent();
                pBlock.GetStatements().Insert(pBlock.GetStatements().IndexOf(pStm), new ALocalDeclStm(new TSemicolon(";"), localDecl));
                reciever = localRefExp;

                data.LvalueTypes[localRef]     =
                    data.ExpTypes[localRefExp] = type;
                data.LocalLinks[localRef]      = localDecl;

                localDecl.Apply(this);
            }

            if (type is ANamedType && finalTrans.data.StructTypeLinks.ContainsKey((ANamedType)type))
            {
                //ANamedType type = (ANamedType) finalTrans.data.ExpTypes[reciever];
                if (finalTrans.data.StructTypeLinks[(ANamedType)type].GetClassToken() != null)
                {
                    //Pass the pointer
                    ALvalueExp     lvalueExp     = (ALvalueExp)reciever;
                    APointerLvalue pointerLvalue = (APointerLvalue)lvalueExp.GetLvalue();
                    reciever = pointerLvalue.GetBase();
                }

                AMethodDecl      method       = finalTrans.data.StructMethodLinks[node];
                ASimpleInvokeExp simpleInvoke = new ASimpleInvokeExp();
                simpleInvoke.SetName(node.GetName());
                PExp[] exps = new PExp[node.GetArgs().Count];
                node.GetArgs().CopyTo(exps, 0);
                foreach (PExp exp in exps)
                {
                    simpleInvoke.GetArgs().Add(exp);
                }
                simpleInvoke.GetArgs().Add(reciever);
                node.ReplaceBy(simpleInvoke);
                finalTrans.data.SimpleMethodLinks[simpleInvoke] = method;
                finalTrans.data.StructMethodLinks.Remove(node);
                finalTrans.data.ExpTypes[simpleInvoke] = method.GetReturnType();
                finalTrans.data.ExpTypes.Remove(node);
                simpleInvoke.Apply(this);
            }
            else
            {//Enrichment
                /*AEnrichmentDecl enrichment = finalTrans.data.EnrichmentTypeLinks[type];
                 *
                 * foreach (AEnrichmentDecl enrichmentDecl in finalTrans.data.Enrichments)
                 * {
                 *  if (Util.IsVisible(node, enrichmentDecl) &&
                 *      Util.IsDeclVisible(enrichmentDecl, Util.GetAncestor<AASourceFile>(node)) &&
                 *      Util.TypesEqual(type, enrichmentDecl.GetType(), finalTrans.data))
                 *  {
                 *      enrichment = enrichmentDecl;
                 *      break;
                 *  }
                 * }
                 * if (enrichment == null)
                 * {
                 *  finalTrans.errors.Add(new ErrorCollection.Error(node.GetName(), "TransFormMethodDecls.NonStaticInvoke: Expected enrichment - this is a bug. It should have been caught earlier"));
                 *  throw new ParserException(node.GetName(), "");
                 * }*/
                AMethodDecl      method       = finalTrans.data.StructMethodLinks[node];
                ASimpleInvokeExp simpleInvoke = new ASimpleInvokeExp();
                simpleInvoke.SetName(node.GetName());
                PExp[] exps = new PExp[node.GetArgs().Count];
                node.GetArgs().CopyTo(exps, 0);
                foreach (PExp exp in exps)
                {
                    simpleInvoke.GetArgs().Add(exp);
                }
                simpleInvoke.GetArgs().Add(reciever);
                node.ReplaceBy(simpleInvoke);
                finalTrans.data.SimpleMethodLinks[simpleInvoke] = method;
                finalTrans.data.StructMethodLinks.Remove(node);
                finalTrans.data.ExpTypes[simpleInvoke] = method.GetReturnType();
                finalTrans.data.ExpTypes.Remove(node);
                simpleInvoke.Apply(this);
            }
        }
        public override void CaseASimpleInvokeExp(ASimpleInvokeExp node)
        {
            AMethodDecl decl = finalTrans.data.SimpleMethodLinks[node];

            if (structMethods.Contains(decl))
            {     //The target is a struct method that has been moved out
                if (node.GetArgs().Count < decl.GetFormals().Count&& Util.HasAncestor <AStructDecl>(node))
                { //If this is the case, we Must be inside the same struct as the target. - Not with enheritance
                    ALocalLvalue local = new ALocalLvalue(new TIdentifier("tempName"));
                    ALvalueExp   exp   = new ALvalueExp(local);
                    finalTrans.data.LvalueTypes[local] =
                        finalTrans.data.ExpTypes[exp]  = structFormal.GetType();
                    finalTrans.data.LocalLinks[local]  = structFormal;

                    //If we're calling from class to struct, we must depointer it
                    AStructDecl currentStruct =
                        finalTrans.data.StructMethods.First(
                            pair => pair.Value.Contains(Util.GetAncestor <AMethodDecl>(node))).Key;
                    AStructDecl baseStruct =
                        finalTrans.data.StructMethods.First(
                            pair => pair.Value.Contains(decl)).Key;
                    if (currentStruct.GetClassToken() != baseStruct.GetClassToken()) //It's not possible to call from struct to class
                    {
                        APointerLvalue pointerLvalue = new APointerLvalue(new TStar("*"), exp);
                        exp = new ALvalueExp(pointerLvalue);

                        finalTrans.data.LvalueTypes[pointerLvalue] =
                            finalTrans.data.ExpTypes[exp]          = ((APointerType)structFormal.GetType()).GetType();
                    }

                    node.GetArgs().Add(exp);
                }
            }
            else if (Util.GetAncestor <AStructDecl>(decl) != null && OldParentStruct.ContainsKey(Util.GetAncestor <AMethodDecl>(node)))
            {     //The target is a struct method that hasn't been moved out
                if (Util.GetAncestor <AStructDecl>(decl) == OldParentStruct[Util.GetAncestor <AMethodDecl>(node)] && decl.GetStatic() == null)
                { //We have an internal struct call. Expect to have one too many args
                    if (node.GetArgs().Count == decl.GetFormals().Count)
                    {
                        ALocalLvalue local = new ALocalLvalue(new TIdentifier("tempName"));
                        ALvalueExp   exp   = new ALvalueExp(local);
                        finalTrans.data.LvalueTypes[local] =
                            finalTrans.data.ExpTypes[exp]  = structFormal.GetType();
                        finalTrans.data.LocalLinks[local]  = structFormal;

                        //If we're calling from class to struct, we must depointer it
                        AStructDecl currentStruct =
                            finalTrans.data.StructMethods.First(
                                pair => pair.Value.Contains(Util.GetAncestor <AMethodDecl>(node))).Key;
                        AStructDecl baseStruct =
                            finalTrans.data.StructMethods.First(
                                pair => pair.Value.Contains(decl)).Key;
                        if (currentStruct.GetClassToken() != baseStruct.GetClassToken()) //It's not possible to call from struct to class
                        {
                            APointerLvalue pointerLvalue = new APointerLvalue(new TStar("*"), exp);
                            exp = new ALvalueExp(pointerLvalue);

                            finalTrans.data.LvalueTypes[pointerLvalue] =
                                finalTrans.data.ExpTypes[exp]          = ((APointerType)structFormal.GetType()).GetType();
                        }

                        node.GetArgs().Add(exp);
                    }
                }
            }
            base.CaseASimpleInvokeExp(node);
        }
Пример #9
0
 private static void MakeCloneRefferences(PLvalue clone, PLvalue lvalue, SharedData data)
 {
     data.LvalueTypes[clone] = data.LvalueTypes[lvalue];
     if (lvalue is ALocalLvalue)
     {
         data.LocalLinks[(ALocalLvalue)clone] = data.LocalLinks[(ALocalLvalue)lvalue];
     }
     else if (lvalue is AFieldLvalue)
     {
         data.FieldLinks[(AFieldLvalue)clone] = data.FieldLinks[(AFieldLvalue)lvalue];
     }
     else if (lvalue is AStructLvalue)
     {
         AStructLvalue aLvalue = (AStructLvalue)lvalue;
         AStructLvalue aClone  = (AStructLvalue)clone;
         if (data.StructFieldLinks.ContainsKey(aLvalue))
         {
             data.StructFieldLinks[aClone] =
                 data.StructFieldLinks[aLvalue];
         }
         else
         {
             data.StructPropertyLinks[aClone] =
                 data.StructPropertyLinks[aLvalue];
         }
         MakeCloneRefferences(aClone.GetReceiver(), aLvalue.GetReceiver(), data);
     }
     else if (lvalue is AStructFieldLvalue)
     {
         AStructFieldLvalue aLvalue = (AStructFieldLvalue)lvalue;
         AStructFieldLvalue aClone  = (AStructFieldLvalue)clone;
         if (data.StructMethodFieldLinks.ContainsKey(aLvalue))
         {
             data.StructMethodFieldLinks[aClone] = data.StructMethodFieldLinks[aLvalue];
         }
         if (data.StructMethodPropertyLinks.ContainsKey(aLvalue))
         {
             data.StructMethodPropertyLinks[aClone] = data.StructMethodPropertyLinks[aLvalue];
         }
     }
     else if (lvalue is AArrayLvalue)
     {
         AArrayLvalue aLvalue = (AArrayLvalue)lvalue;
         AArrayLvalue aClone  = (AArrayLvalue)clone;
         MakeCloneRefferences(aClone.GetBase(), aLvalue.GetBase(), data);
         MakeCloneRefferences(aClone.GetIndex(), aLvalue.GetIndex(), data);
     }
     else if (lvalue is APointerLvalue)
     {
         APointerLvalue aLvalue = (APointerLvalue)lvalue;
         APointerLvalue aClone  = (APointerLvalue)clone;
         MakeCloneRefferences(aClone.GetBase(), aLvalue.GetBase(), data);
     }
     else if (lvalue is AThisLvalue || lvalue is AValueLvalue)
     {
         //AThisLvalue aLvalue = (AThisLvalue)lvalue;
         //Do nothing more
     }
     else if (lvalue is APropertyLvalue)
     {
         APropertyLvalue aLvalue = (APropertyLvalue)lvalue;
         APropertyLvalue aClone  = (APropertyLvalue)clone;
         data.PropertyLinks[aClone] = data.PropertyLinks[aLvalue];
     }
     else
     {
         throw new Exception("Unexpect lvalue. Got " + lvalue.GetType());
     }
 }