private void SerializeNamespaceScopeMetadata(IMethodBody methodBody, ArrayBuilder <MemoryStream> customDebugInfo)
        {
            if (methodBody.NamespaceScopeEncoding == NamespaceScopeEncoding.Forwarding)
            {
                return;
            }

            if (ShouldForwardToPreviousMethodWithUsingInfo(methodBody))
            {
                Debug.Assert(!ReferenceEquals(_previousMethodBodyWithUsingInfo, methodBody));
                SerializeReferenceToPreviousMethodWithUsingInfo(customDebugInfo);
                return;
            }

            MemoryStream  customMetadata = new MemoryStream();
            List <ushort> usingCounts    = new List <ushort>();
            BinaryWriter  cmw            = new BinaryWriter(customMetadata);

            foreach (NamespaceScope namespaceScope in methodBody.NamespaceScopes)
            {
                usingCounts.Add((ushort)namespaceScope.UsedNamespaces.Length);
            }

            // ACASEY: This originally wrote (uint)12, (ushort)1, (ushort)0 in the
            // case where usingCounts was empty, but I'm not sure why.
            if (usingCounts.Count > 0)
            {
                uint streamLength = 0;
                cmw.WriteByte(CDI.CdiVersion);
                cmw.WriteByte(CDI.CdiKindUsingInfo);
                cmw.Align(4);

                cmw.WriteUint(streamLength = BitArithmeticUtilities.Align((uint)usingCounts.Count * 2 + 10, 4));
                cmw.WriteUshort((ushort)usingCounts.Count);
                foreach (ushort uc in usingCounts)
                {
                    cmw.WriteUshort(uc);
                }

                cmw.Align(4);
                Debug.Assert(streamLength == customMetadata.Length);
                customDebugInfo.Add(customMetadata);
            }

            if (_methodBodyWithModuleInfo != null && !ReferenceEquals(_methodBodyWithModuleInfo, methodBody))
            {
                SerializeReferenceToMethodWithModuleInfo(customDebugInfo);
            }
        }
Beispiel #2
0
        private void SerializeNamespaceScopeMetadata(EmitContext context, IMethodBody methodBody, ArrayBuilder <MemoryStream> customDebugInfo)
        {
            if (context.Module.GenerateVisualBasicStylePdb)
            {
                return;
            }

            if (ShouldForwardToPreviousMethodWithUsingInfo(context, methodBody))
            {
                Debug.Assert(!ReferenceEquals(_previousMethodBodyWithUsingInfo, methodBody));
                SerializeReferenceToPreviousMethodWithUsingInfo(customDebugInfo);
                return;
            }

            MemoryStream  customMetadata = new MemoryStream();
            List <ushort> usingCounts    = new List <ushort>();
            BinaryWriter  cmw            = new BinaryWriter(customMetadata);

            for (IImportScope scope = methodBody.ImportScope; scope != null; scope = scope.Parent)
            {
                usingCounts.Add((ushort)scope.GetUsedNamespaces().Length);
            }

            // ACASEY: This originally wrote (uint)12, (ushort)1, (ushort)0 in the
            // case where usingCounts was empty, but I'm not sure why.
            if (usingCounts.Count > 0)
            {
                uint streamLength;
                cmw.WriteByte(CDI.CdiVersion);
                cmw.WriteByte(CDI.CdiKindUsingInfo);
                cmw.Align(4);

                cmw.WriteUint(streamLength = BitArithmeticUtilities.Align((uint)usingCounts.Count * 2 + 10, 4));
                cmw.WriteUshort((ushort)usingCounts.Count);
                foreach (ushort uc in usingCounts)
                {
                    cmw.WriteUshort(uc);
                }

                cmw.Align(4);
                Debug.Assert(streamLength == customMetadata.Length);
                customDebugInfo.Add(customMetadata);
            }

            if (_methodBodyWithModuleInfo != null && !ReferenceEquals(_methodBodyWithModuleInfo, methodBody))
            {
                SerializeReferenceToMethodWithModuleInfo(customDebugInfo);
            }
        }
        public void WriteData(BinaryWriter resourceWriter)
        {
            if (fileReference == null)
            {
                try
                {
                    using (Stream stream = streamProvider())
                    {
                        if (stream == null)
                        {
                            throw new InvalidOperationException(CodeAnalysisResources.ResourceStreamProviderShouldReturnNonNullStream);
                        }

                        var count = (int)(stream.Length - stream.Position);
                        resourceWriter.WriteInt(count);

                        var to       = resourceWriter.BaseStream;
                        var position = (int)to.Position;
                        to.Position = (uint)(position + count);
                        resourceWriter.Align(8);

                        var buffer = to.Buffer;
                        stream.Read(buffer, position, count);
                    }
                }
                catch (Exception e)
                {
                    throw new ResourceException(this.name, e);
                }
            }
        }
Beispiel #4
0
        private static void SerializeIteratorLocalScopes(IMethodBody methodBody, ArrayBuilder <MemoryStream> customDebugInfo)
        {
            ImmutableArray <LocalScope> scopes = methodBody.IteratorScopes;
            uint numberOfScopes = (uint)scopes.Length;

            if (numberOfScopes == 0)
            {
                return;
            }

            MemoryStream customMetadata = new MemoryStream();
            BinaryWriter cmw            = new BinaryWriter(customMetadata);

            cmw.WriteByte(4); // version
            cmw.WriteByte(3); // kind: IteratorLocals
            cmw.Align(4);
            cmw.WriteUint(12 + numberOfScopes * 8);
            cmw.WriteUint(numberOfScopes);
            foreach (var scope in scopes)
            {
                cmw.WriteUint(scope.Offset);
                cmw.WriteUint(scope.Offset + scope.Length);
            }

            customDebugInfo.Add(customMetadata);
        }
        private static void SerializeStateMachineLocalScopes(IMethodBody methodBody, ArrayBuilder <MemoryStream> customDebugInfo)
        {
            var scopes = methodBody.StateMachineHoistedLocalScopes;

            if (scopes.IsDefaultOrEmpty)
            {
                return;
            }

            uint         numberOfScopes = (uint)scopes.Length;
            MemoryStream customMetadata = new MemoryStream();
            BinaryWriter cmw            = new BinaryWriter(customMetadata);

            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte(CDI.CdiKindStateMachineHoistedLocalScopes);
            cmw.Align(4);
            cmw.WriteUint(12 + numberOfScopes * 8);
            cmw.WriteUint(numberOfScopes);
            foreach (var scope in scopes)
            {
                cmw.WriteUint(scope.StartOffset);
                cmw.WriteUint(scope.EndOffset);
            }

            customDebugInfo.Add(customMetadata);
        }
        public void WriteData(BinaryWriter resourceWriter)
        {
            if (fileReference == null)
            {
                try
                {
                    using (Stream stream = streamProvider())
                    {
                        if (stream == null)
                        {
                            throw new InvalidOperationException(CodeAnalysisResources.ResourceStreamProviderShouldReturnNonNullStream);
                        }

                        var count = (int)(stream.Length - stream.Position);
                        resourceWriter.WriteInt(count);

                        var to = resourceWriter.BaseStream;
                        var position = (int)to.Position;
                        to.Position = (uint)(position + count);
                        resourceWriter.Align(8);

                        var buffer = to.Buffer;
                        stream.Read(buffer, position, count);
                    }
                }
                catch (Exception e)
                {
                    throw new ResourceException(this.name, e);
                }
            }
        }
Beispiel #7
0
        private void SerializeReferenceToMethodWithModuleInfo(ArrayBuilder <MemoryStream> customDebugInfo)
        {
            MemoryStream customMetadata = new MemoryStream(12);
            BinaryWriter cmw            = new BinaryWriter(customMetadata);

            cmw.WriteByte(4); // version
            cmw.WriteByte(2); // kind: ForwardToModuleInfo
            cmw.Align(4);
            cmw.WriteUint(12);
            cmw.WriteUint(this.methodTokenWithModuleInfo);
            customDebugInfo.Add(customMetadata);
        }
        private void SerializeReferenceToPreviousMethodWithUsingInfo(ArrayBuilder <MemoryStream> customDebugInfo)
        {
            MemoryStream customMetadata = new MemoryStream(12);
            BinaryWriter cmw            = new BinaryWriter(customMetadata);

            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte(CDI.CdiKindForwardInfo);
            cmw.Align(4);
            cmw.WriteUint(12);
            cmw.WriteUint(_previousMethodTokenWithUsingInfo);
            customDebugInfo.Add(customMetadata);
        }
        private static void SerializeReferenceToIteratorClass(string iteratorClassName, ArrayBuilder <MemoryStream> customDebugInfo)
        {
            if (iteratorClassName == null)
            {
                return;
            }
            MemoryStream customMetadata = new MemoryStream();
            BinaryWriter cmw            = new BinaryWriter(customMetadata, true);

            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte(CDI.CdiKindForwardIterator);
            cmw.Align(4);
            uint length = 10 + (uint)iteratorClassName.Length * 2;

            if ((length & 3) != 0)
            {
                length += 4 - (length & 3);
            }
            cmw.WriteUint(length);
            cmw.WriteString(iteratorClassName, true);
            cmw.Align(4);
            Debug.Assert(customMetadata.Position == length);
            customDebugInfo.Add(customMetadata);
        }
Beispiel #10
0
        private static MemoryStream SerializeRecord(byte kind, Action <BinaryWriter> data)
        {
            MemoryStream customMetadata = new MemoryStream();
            BinaryWriter cmw            = new BinaryWriter(customMetadata);

            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte(kind);
            cmw.Align(4);

            // length (will be patched)
            uint lengthPosition = cmw.BaseStream.Position;

            cmw.WriteUint(0);

            data(cmw);

            uint length = customMetadata.Position;

            cmw.BaseStream.Position = lengthPosition;
            cmw.WriteUint(length);
            cmw.BaseStream.Position = length;
            return(customMetadata);
        }
        private static byte[] SerializeCustomDebugMetadata(ArrayBuilder <MemoryStream> customDebugInfo)
        {
            if (customDebugInfo.Count == 0)
            {
                return(null);
            }

            MemoryStream customMetadata = MemoryStream.GetInstance();
            BinaryWriter cmw            = new BinaryWriter(customMetadata);

            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte((byte)customDebugInfo.Count); // count
            cmw.Align(4);
            foreach (MemoryStream ms in customDebugInfo)
            {
                ms.WriteTo(customMetadata);
            }

            var result = customMetadata.ToArray();

            customMetadata.Free();
            return(result);
        }
 private void SerializeReferenceToPreviousMethodWithUsingInfo(ArrayBuilder<MemoryStream> customDebugInfo)
 {
     MemoryStream customMetadata = new MemoryStream(12);
     BinaryWriter cmw = new BinaryWriter(customMetadata);
     cmw.WriteByte(CDI.CdiVersion);
     cmw.WriteByte(CDI.CdiKindForwardInfo);
     cmw.Align(4);
     cmw.WriteUint(12);
     cmw.WriteUint(_previousMethodTokenWithUsingInfo);
     customDebugInfo.Add(customMetadata);
 }
        private static MemoryStream SerializeRecord(byte kind, Action<BinaryWriter> data)
        {
            MemoryStream customMetadata = new MemoryStream();
            BinaryWriter cmw = new BinaryWriter(customMetadata);
            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte(kind);
            cmw.Align(4);

            // length (will be patched)
            uint lengthPosition = cmw.BaseStream.Position;
            cmw.WriteUint(0);

            data(cmw);

            uint length = customMetadata.Position;
            cmw.BaseStream.Position = lengthPosition;
            cmw.WriteUint(length);
            cmw.BaseStream.Position = length;
            return customMetadata;
        }
        private static void SerializeDynamicLocalInfo(IMethodBody methodBody, ArrayBuilder <MemoryStream> customDebugInfo)
        {
            if (!methodBody.HasDynamicLocalVariables)
            {
                return; //There are no dynamic locals
            }

            var dynamicLocals = ArrayBuilder <ILocalDefinition> .GetInstance();

            foreach (ILocalDefinition local in methodBody.LocalVariables)
            {
                if (local.IsDynamic)
                {
                    dynamicLocals.Add(local);
                }
            }

            int dynamicVariableCount = dynamicLocals.Count;

            foreach (var currentScope in methodBody.LocalScopes)
            {
                foreach (var localConstant in currentScope.Constants)
                {
                    if (localConstant.IsDynamic)
                    {
                        dynamicLocals.Add(localConstant);
                    }
                }
            }

            Debug.Assert(dynamicLocals.Any()); // There must be atleast one dynamic local if this point is reached

            const int    blobSize       = 200; //DynamicAttribute - 64, DynamicAttributeLength - 4, SlotIndex -4, IdentifierName - 128
            MemoryStream customMetadata = new MemoryStream();
            BinaryWriter cmw            = new BinaryWriter(customMetadata, true);

            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte(CDI.CdiKindDynamicLocals);
            cmw.Align(4);
            // size = Version,Kind + size + cBuckets + (dynamicCount * sizeOf(Local Blob))
            cmw.WriteUint(4 + 4 + 4 + (uint)dynamicLocals.Count * blobSize);//Size of the Dynamic Block
            cmw.WriteUint((uint)dynamicLocals.Count);

            int localIndex = 0;

            foreach (ILocalDefinition local in dynamicLocals)
            {
                if (local.Name.Length > 63)//Ignore and push empty information
                {
                    cmw.WriteBytes(0, blobSize);
                    continue;
                }

                var dynamicTransformFlags = local.DynamicTransformFlags;
                if (!dynamicTransformFlags.IsDefault && dynamicTransformFlags.Length <= 64)
                {
                    byte[] flag = new byte[64];
                    for (int k = 0; k < dynamicTransformFlags.Length; k++)
                    {
                        if ((bool)dynamicTransformFlags[k].Value)
                        {
                            flag[k] = (byte)1;
                        }
                    }
                    cmw.WriteBytes(flag);                              //Written Flag
                    cmw.WriteUint((uint)dynamicTransformFlags.Length); //Written Length
                }
                else
                {
                    cmw.WriteBytes(0, 68); //Empty flag array and size.
                }

                if (localIndex < dynamicVariableCount)
                {
                    // Dynamic variable
                    cmw.WriteUint((uint)local.SlotIndex);
                }
                else
                {
                    // Dynamic constant
                    cmw.WriteUint(0);
                }

                char[] localName = new char[64];
                local.Name.CopyTo(0, localName, 0, local.Name.Length);
                cmw.WriteChars(localName);

                localIndex++;
            }

            dynamicLocals.Free();
            customDebugInfo.Add(customMetadata);
        }
 private static void SerializeReferenceToIteratorClass(string iteratorClassName, ArrayBuilder<MemoryStream> customDebugInfo)
 {
     if (iteratorClassName == null) return;
     MemoryStream customMetadata = new MemoryStream();
     BinaryWriter cmw = new BinaryWriter(customMetadata, true);
     cmw.WriteByte(CDI.CdiVersion);
     cmw.WriteByte(CDI.CdiKindForwardIterator);
     cmw.Align(4);
     uint length = 10 + (uint)iteratorClassName.Length * 2;
     if ((length & 3) != 0) length += 4 - (length & 3);
     cmw.WriteUint(length);
     cmw.WriteString(iteratorClassName, true);
     cmw.Align(4);
     Debug.Assert(customMetadata.Position == length);
     customDebugInfo.Add(customMetadata);
 }
        private static void SerializeStateMachineLocalScopes(IMethodBody methodBody, ArrayBuilder<MemoryStream> customDebugInfo)
        {
            var scopes = methodBody.StateMachineHoistedLocalScopes;
            if (scopes.IsDefaultOrEmpty)
            {
                return;
            }

            uint numberOfScopes = (uint)scopes.Length;
            MemoryStream customMetadata = new MemoryStream();
            BinaryWriter cmw = new BinaryWriter(customMetadata);
            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte(CDI.CdiKindStateMachineHoistedLocalScopes);
            cmw.Align(4);
            cmw.WriteUint(12 + numberOfScopes * 8);
            cmw.WriteUint(numberOfScopes);
            foreach (var scope in scopes)
            {
                if (scope.IsDefault)
                {
                    cmw.WriteUint(0);
                    cmw.WriteUint(0);
                }
                else
                {
                    // Dev12 C# emits end-inclusive range
                    cmw.WriteUint((uint)scope.StartOffset);
                    cmw.WriteUint((uint)scope.EndOffset - 1);
                }
            }

            customDebugInfo.Add(customMetadata);
        }
        private static void SerializeDynamicLocalInfo(IMethodBody methodBody, ArrayBuilder<MemoryStream> customDebugInfo)
        {
            if (!methodBody.HasDynamicLocalVariables)
            {
                return; //There are no dynamic locals
            }

            var dynamicLocals = ArrayBuilder<ILocalDefinition>.GetInstance();

            foreach (ILocalDefinition local in methodBody.LocalVariables)
            {
                if (local.IsDynamic)
                {
                    dynamicLocals.Add(local);
                }
            }

            int dynamicVariableCount = dynamicLocals.Count;

            foreach (var currentScope in methodBody.LocalScopes)
            {
                foreach (var localConstant in currentScope.Constants)
                {
                    if (localConstant.IsDynamic)
                    {
                        dynamicLocals.Add(localConstant);
                    }
                }
            }

            Debug.Assert(dynamicLocals.Any()); // There must be atleast one dynamic local if this point is reached

            const int blobSize = 200;//DynamicAttribute - 64, DynamicAttributeLength - 4, SlotIndex -4, IdentifierName - 128
            MemoryStream customMetadata = new MemoryStream();
            BinaryWriter cmw = new BinaryWriter(customMetadata, true);
            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte(CDI.CdiKindDynamicLocals);
            cmw.Align(4);
            // size = Version,Kind + size + cBuckets + (dynamicCount * sizeOf(Local Blob))
            cmw.WriteUint(4 + 4 + 4 + (uint)dynamicLocals.Count * blobSize);//Size of the Dynamic Block
            cmw.WriteUint((uint)dynamicLocals.Count);

            int localIndex = 0;
            foreach (ILocalDefinition local in dynamicLocals)
            {
                if (local.Name.Length > 63)//Ignore and push empty information
                {
                    cmw.WriteBytes(0, blobSize);
                    continue;
                }

                var dynamicTransformFlags = local.DynamicTransformFlags;
                if (!dynamicTransformFlags.IsDefault && dynamicTransformFlags.Length <= 64)
                {
                    byte[] flag = new byte[64];
                    for (int k = 0; k < dynamicTransformFlags.Length; k++)
                    {
                        if ((bool)dynamicTransformFlags[k].Value)
                        {
                            flag[k] = (byte)1;
                        }
                    }
                    cmw.WriteBytes(flag); //Written Flag
                    cmw.WriteUint((uint)dynamicTransformFlags.Length); //Written Length
                }
                else
                {
                    cmw.WriteBytes(0, 68); //Empty flag array and size.
                }

                if (localIndex < dynamicVariableCount)
                {
                    // Dynamic variable
                    cmw.WriteUint((uint)local.SlotIndex);
                }
                else
                {
                    // Dynamic constant
                    cmw.WriteUint(0);
                }

                char[] localName = new char[64];
                local.Name.CopyTo(0, localName, 0, local.Name.Length);
                cmw.WriteChars(localName);

                localIndex++;
            }

            dynamicLocals.Free();
            customDebugInfo.Add(customMetadata);
        }
        private static byte[] SerializeCustomDebugMetadata(ArrayBuilder<MemoryStream> customDebugInfo)
        {
            if (customDebugInfo.Count == 0)
            {
                return null;
            }

            MemoryStream customMetadata = MemoryStream.GetInstance();
            BinaryWriter cmw = new BinaryWriter(customMetadata);
            cmw.WriteByte(CDI.CdiVersion);
            cmw.WriteByte((byte)customDebugInfo.Count); // count
            cmw.Align(4);
            foreach (MemoryStream ms in customDebugInfo)
            {
                ms.WriteTo(customMetadata);
            }

            var result = customMetadata.ToArray();
            customMetadata.Free();
            return result;
        }
        private void SerializeNamespaceScopeMetadata(EmitContext context, IMethodBody methodBody, ArrayBuilder<MemoryStream> customDebugInfo)
        {
            if (context.Module.GenerateVisualBasicStylePdb)
            {
                return;
            }

            if (ShouldForwardToPreviousMethodWithUsingInfo(context, methodBody))
            {
                Debug.Assert(!ReferenceEquals(_previousMethodBodyWithUsingInfo, methodBody));
                SerializeReferenceToPreviousMethodWithUsingInfo(customDebugInfo);
                return;
            }

            MemoryStream customMetadata = new MemoryStream();
            List<ushort> usingCounts = new List<ushort>();
            BinaryWriter cmw = new BinaryWriter(customMetadata);
            for (IImportScope scope = methodBody.ImportScope; scope != null; scope = scope.Parent)
            {
                usingCounts.Add((ushort)scope.GetUsedNamespaces(context).Length);
            }

            // ACASEY: This originally wrote (uint)12, (ushort)1, (ushort)0 in the
            // case where usingCounts was empty, but I'm not sure why.
            if (usingCounts.Count > 0)
            {
                uint streamLength = 0;
                cmw.WriteByte(CDI.CdiVersion);
                cmw.WriteByte(CDI.CdiKindUsingInfo);
                cmw.Align(4);

                cmw.WriteUint(streamLength = BitArithmeticUtilities.Align((uint)usingCounts.Count * 2 + 10, 4));
                cmw.WriteUshort((ushort)usingCounts.Count);
                foreach (ushort uc in usingCounts)
                {
                    cmw.WriteUshort(uc);
                }

                cmw.Align(4);
                Debug.Assert(streamLength == customMetadata.Length);
                customDebugInfo.Add(customMetadata);
            }

            if (_methodBodyWithModuleInfo != null && !ReferenceEquals(_methodBodyWithModuleInfo, methodBody))
            {
                SerializeReferenceToMethodWithModuleInfo(customDebugInfo);
            }
        }