コード例 #1
0
ファイル: GenericsConverter.cs プロジェクト: Xtremrules/dot42
        private static void ConvertUnboxStruct(AstExpression node, XTypeReference resultType, XTypeSystem typeSystem)
        {
            // Structs must never be null. We have to handle structs here, since a newobj 
            // might need generic arguments. These would be difficult to provide at "UnboxFromGeneric",
            // but will be automatically filled in by the GenericInstanceConverter

            // convert to (temp$ = (T)x) != null ? temp$ : default(T)

            // replace any unbox, but keep if otherwise.
            var clone = node.Code == AstCode.Unbox ? new AstExpression(node.Arguments[0]) : new AstExpression(node);

            // make sure we don't evaluate the expression twice.
            var tempVar = new AstGeneratedVariable("temp$", "") { Type = typeSystem.Object };

            // T(x)
            var txExpr = new AstExpression(node.SourceLocation, AstCode.SimpleCastclass, resultType, clone)
                                .SetType(resultType);

            // temporary storage
            var storeTempVar = new AstExpression(node.SourceLocation, AstCode.Stloc, tempVar, txExpr) { ExpectedType = resultType };
            var loadTempVar = new AstExpression(node.SourceLocation, AstCode.Ldloc, tempVar)
                                .SetType(resultType);

            // default (T)
            var defaultT = new AstExpression(node.SourceLocation, AstCode.DefaultValue, resultType).SetType(resultType);
            var constructor = StructCallConverter.GetDefaultValueCtor(resultType.Resolve());
            StructCallConverter.ConvertDefaultValue(defaultT, constructor);

            // Combine
            var conditional = new AstExpression(node.SourceLocation, AstCode.Conditional, resultType,
                                                storeTempVar, loadTempVar, defaultT)
                                .SetType(resultType);

            node.CopyFrom(conditional);
        }