private void ReadXmlSecurityAttribute(ref SRM.BlobReader reader, CustomAttributeTypedArgument <IType> securityAction) { string xml = reader.ReadUTF16(reader.RemainingBytes); var b = new AttributeBuilder(module, KnownAttribute.PermissionSet); b.AddFixedArg(securityAction); b.AddNamedArg("XML", KnownTypeCode.String, xml); }
IAttribute ConvertMarshalInfo(SRM.BlobReader marshalInfo) { var b = new AttributeBuilder(module, KnownAttribute.MarshalAs); IType unmanagedTypeType = module.Compilation.FindType(new TopLevelTypeName(InteropServices, nameof(UnmanagedType))); int type = marshalInfo.ReadByte(); b.AddFixedArg(unmanagedTypeType, type); int size; switch (type) { case 0x1e: // FixedArray if (!marshalInfo.TryReadCompressedInteger(out size)) { size = 0; } b.AddNamedArg("SizeConst", KnownTypeCode.Int32, size); if (marshalInfo.RemainingBytes > 0) { type = marshalInfo.ReadByte(); if (type != 0x66) // None { b.AddNamedArg("ArraySubType", unmanagedTypeType, type); } } break; case 0x1d: // SafeArray if (marshalInfo.RemainingBytes > 0) { VarEnum varType = (VarEnum)marshalInfo.ReadByte(); if (varType != VarEnum.VT_EMPTY) { var varEnumType = new TopLevelTypeName(InteropServices, nameof(VarEnum)); b.AddNamedArg("SafeArraySubType", varEnumType, (int)varType); } } break; case 0x2a: // NATIVE_TYPE_ARRAY if (marshalInfo.RemainingBytes > 0) { type = marshalInfo.ReadByte(); } else { type = 0x66; // Cecil uses NativeType.None as default. } if (type != 0x50) // Max { b.AddNamedArg("ArraySubType", unmanagedTypeType, type); } int sizeParameterIndex = marshalInfo.TryReadCompressedInteger(out int value) ? value : -1; size = marshalInfo.TryReadCompressedInteger(out value) ? value : -1; int sizeParameterMultiplier = marshalInfo.TryReadCompressedInteger(out value) ? value : -1; if (size >= 0) { b.AddNamedArg("SizeConst", KnownTypeCode.Int32, size); } if (sizeParameterMultiplier != 0 && sizeParameterIndex >= 0) { b.AddNamedArg("SizeParamIndex", KnownTypeCode.Int16, (short)sizeParameterIndex); } break; case 0x2c: // CustomMarshaler string guidValue = marshalInfo.ReadSerializedString(); string unmanagedType = marshalInfo.ReadSerializedString(); string managedType = marshalInfo.ReadSerializedString(); string cookie = marshalInfo.ReadSerializedString(); if (managedType != null) { b.AddNamedArg("MarshalType", KnownTypeCode.String, managedType); } if (!string.IsNullOrEmpty(cookie)) { b.AddNamedArg("MarshalCookie", KnownTypeCode.String, cookie); } break; case 0x17: // FixedSysString b.AddNamedArg("SizeConst", KnownTypeCode.Int32, marshalInfo.ReadCompressedInteger()); break; } return(b.Build()); }
public IEnumerable <IAttribute> GetAttributes() { var b = new AttributeListBuilder(module); var metadata = module.metadata; var typeDefinition = metadata.GetTypeDefinition(handle); // SerializableAttribute if ((typeDefinition.Attributes & TypeAttributes.Serializable) != 0) { b.Add(KnownAttribute.Serializable); } // ComImportAttribute if ((typeDefinition.Attributes & TypeAttributes.Import) != 0) { b.Add(KnownAttribute.ComImport); } #region StructLayoutAttribute LayoutKind layoutKind = LayoutKind.Auto; switch (typeDefinition.Attributes & TypeAttributes.LayoutMask) { case TypeAttributes.SequentialLayout: layoutKind = LayoutKind.Sequential; break; case TypeAttributes.ExplicitLayout: layoutKind = LayoutKind.Explicit; break; } CharSet charSet = CharSet.None; switch (typeDefinition.Attributes & TypeAttributes.StringFormatMask) { case TypeAttributes.AnsiClass: charSet = CharSet.Ansi; break; case TypeAttributes.AutoClass: charSet = CharSet.Auto; break; case TypeAttributes.UnicodeClass: charSet = CharSet.Unicode; break; } var layout = typeDefinition.GetLayout(); LayoutKind defaultLayoutKind = Kind == TypeKind.Struct ? LayoutKind.Sequential : LayoutKind.Auto; if (layoutKind != defaultLayoutKind || charSet != CharSet.Ansi || layout.PackingSize > 0 || layout.Size > 0) { var structLayout = new AttributeBuilder(module, KnownAttribute.StructLayout); structLayout.AddFixedArg( new TopLevelTypeName("System.Runtime.InteropServices", "LayoutKind"), (int)layoutKind); if (charSet != CharSet.Ansi) { var charSetType = Compilation.FindType(new TopLevelTypeName("System.Runtime.InteropServices", "CharSet")); structLayout.AddNamedArg("CharSet", charSetType, (int)charSet); } if (layout.PackingSize > 0) { structLayout.AddNamedArg("Pack", KnownTypeCode.Int32, (int)layout.PackingSize); } if (layout.Size > 0) { structLayout.AddNamedArg("Size", KnownTypeCode.Int32, (int)layout.Size); } b.Add(structLayout.Build()); } #endregion b.Add(typeDefinition.GetCustomAttributes(), SymbolKind.TypeDefinition); b.AddSecurityAttributes(typeDefinition.GetDeclarativeSecurityAttributes()); return(b.Build()); }
public IEnumerable <IAttribute> GetAttributes() { var b = new AttributeListBuilder(module); var metadata = module.metadata; var def = metadata.GetMethodDefinition(handle); MethodImplAttributes implAttributes = def.ImplAttributes & ~MethodImplAttributes.CodeTypeMask; #region DllImportAttribute var info = def.GetImport(); if ((attributes & MethodAttributes.PinvokeImpl) == MethodAttributes.PinvokeImpl && !info.Module.IsNil) { var dllImport = new AttributeBuilder(module, KnownAttribute.DllImport); dllImport.AddFixedArg(KnownTypeCode.String, metadata.GetString(metadata.GetModuleReference(info.Module).Name)); var importAttrs = info.Attributes; if ((importAttrs & MethodImportAttributes.BestFitMappingDisable) == MethodImportAttributes.BestFitMappingDisable) { dllImport.AddNamedArg("BestFitMapping", KnownTypeCode.Boolean, false); } if ((importAttrs & MethodImportAttributes.BestFitMappingEnable) == MethodImportAttributes.BestFitMappingEnable) { dllImport.AddNamedArg("BestFitMapping", KnownTypeCode.Boolean, true); } CallingConvention callingConvention; switch (info.Attributes & MethodImportAttributes.CallingConventionMask) { case 0: Debug.WriteLine($"P/Invoke calling convention not set on: {this}"); callingConvention = 0; break; case MethodImportAttributes.CallingConventionCDecl: callingConvention = CallingConvention.Cdecl; break; case MethodImportAttributes.CallingConventionFastCall: callingConvention = CallingConvention.FastCall; break; case MethodImportAttributes.CallingConventionStdCall: callingConvention = CallingConvention.StdCall; break; case MethodImportAttributes.CallingConventionThisCall: callingConvention = CallingConvention.ThisCall; break; case MethodImportAttributes.CallingConventionWinApi: callingConvention = CallingConvention.Winapi; break; default: throw new NotSupportedException("unknown calling convention"); } if (callingConvention != CallingConvention.Winapi) { var callingConventionType = FindInteropType(nameof(CallingConvention)); dllImport.AddNamedArg("CallingConvention", callingConventionType, (int)callingConvention); } CharSet charSet = CharSet.None; switch (info.Attributes & MethodImportAttributes.CharSetMask) { case MethodImportAttributes.CharSetAnsi: charSet = CharSet.Ansi; break; case MethodImportAttributes.CharSetAuto: charSet = CharSet.Auto; break; case MethodImportAttributes.CharSetUnicode: charSet = CharSet.Unicode; break; } if (charSet != CharSet.None) { var charSetType = FindInteropType(nameof(CharSet)); dllImport.AddNamedArg("CharSet", charSetType, (int)charSet); } if (!info.Name.IsNil && info.Name != def.Name) { dllImport.AddNamedArg("EntryPoint", KnownTypeCode.String, metadata.GetString(info.Name)); } if ((info.Attributes & MethodImportAttributes.ExactSpelling) == MethodImportAttributes.ExactSpelling) { dllImport.AddNamedArg("ExactSpelling", KnownTypeCode.Boolean, true); } if ((implAttributes & MethodImplAttributes.PreserveSig) == MethodImplAttributes.PreserveSig) { implAttributes &= ~MethodImplAttributes.PreserveSig; } else { dllImport.AddNamedArg("PreserveSig", KnownTypeCode.Boolean, false); } if ((info.Attributes & MethodImportAttributes.SetLastError) == MethodImportAttributes.SetLastError) { dllImport.AddNamedArg("SetLastError", KnownTypeCode.Boolean, true); } if ((info.Attributes & MethodImportAttributes.ThrowOnUnmappableCharDisable) == MethodImportAttributes.ThrowOnUnmappableCharDisable) { dllImport.AddNamedArg("ThrowOnUnmappableChar", KnownTypeCode.Boolean, false); } if ((info.Attributes & MethodImportAttributes.ThrowOnUnmappableCharEnable) == MethodImportAttributes.ThrowOnUnmappableCharEnable) { dllImport.AddNamedArg("ThrowOnUnmappableChar", KnownTypeCode.Boolean, true); } b.Add(dllImport.Build()); } #endregion #region PreserveSigAttribute if (implAttributes == MethodImplAttributes.PreserveSig) { b.Add(KnownAttribute.PreserveSig); implAttributes = 0; } #endregion #region MethodImplAttribute if (implAttributes != 0) { b.Add(KnownAttribute.MethodImpl, new TopLevelTypeName("System.Runtime.CompilerServices", nameof(MethodImplOptions)), (int)implAttributes ); } #endregion b.Add(def.GetCustomAttributes(), symbolKind); b.AddSecurityAttributes(def.GetDeclarativeSecurityAttributes()); return(b.Build()); }