internal static PEPropertySymbol Create( PEModuleSymbol moduleSymbol, PENamedTypeSymbol containingType, PropertyDefinitionHandle handle, PEMethodSymbol getMethod, PEMethodSymbol setMethod) { Debug.Assert((object)moduleSymbol != null); Debug.Assert((object)containingType != null); Debug.Assert(!handle.IsNil); var metadataDecoder = new MetadataDecoder(moduleSymbol, containingType); SignatureHeader callingConvention; BadImageFormatException propEx; var propertyParams = metadataDecoder.GetSignatureForProperty(handle, out callingConvention, out propEx); Debug.Assert(propertyParams.Length > 0); var returnInfo = propertyParams[0]; PEPropertySymbol result = returnInfo.CustomModifiers.IsDefaultOrEmpty && returnInfo.RefCustomModifiers.IsDefaultOrEmpty ? new PEPropertySymbol(moduleSymbol, containingType, handle, getMethod, setMethod, propertyParams, metadataDecoder) : new PEPropertySymbolWithCustomModifiers(moduleSymbol, containingType, handle, getMethod, setMethod, propertyParams, metadataDecoder); // A property should always have this modreq, and vice versa. var isBad = (result.RefKind == RefKind.In) != result.RefCustomModifiers.HasInAttributeModifier(); if (propEx != null || isBad) { result._lazyUseSiteDiagnostic = new CSDiagnosticInfo(ErrorCode.ERR_BindToBogus, result); } return(result); }
internal PEPropertySymbol( PEModuleSymbol moduleSymbol, PENamedTypeSymbol containingType, PropertyDefinitionHandle handle, PEMethodSymbol getMethod, PEMethodSymbol setMethod) { Debug.Assert((object)moduleSymbol != null); Debug.Assert((object)containingType != null); Debug.Assert(!handle.IsNil); _containingType = containingType; var module = moduleSymbol.Module; PropertyAttributes mdFlags = 0; BadImageFormatException mrEx = null; try { module.GetPropertyDefPropsOrThrow(handle, out _name, out mdFlags); } catch (BadImageFormatException e) { mrEx = e; if ((object)_name == null) { _name = string.Empty; } } _getMethod = getMethod; _setMethod = setMethod; _handle = handle; var metadataDecoder = new MetadataDecoder(moduleSymbol, containingType); SignatureHeader callingConvention; BadImageFormatException propEx; var propertyParams = metadataDecoder.GetSignatureForProperty(handle, out callingConvention, out propEx, allowByRefReturn: true); Debug.Assert(propertyParams.Length > 0); SignatureHeader unusedCallingConvention; BadImageFormatException getEx = null; var getMethodParams = (object)getMethod == null ? null : metadataDecoder.GetSignatureForMethod(getMethod.Handle, out unusedCallingConvention, out getEx, allowByRefReturn: true); BadImageFormatException setEx = null; var setMethodParams = (object)setMethod == null ? null : metadataDecoder.GetSignatureForMethod(setMethod.Handle, out unusedCallingConvention, out setEx, allowByRefReturn: false); // NOTE: property parameter names are not recorded in metadata, so we have to // use the parameter names from one of the indexers // NB: prefer setter names to getter names if both are present. bool isBad; _parameters = GetParameters(moduleSymbol, this, propertyParams, setMethodParams ?? getMethodParams, out isBad); if (propEx != null || getEx != null || setEx != null || mrEx != null || isBad) { _lazyUseSiteDiagnostic = new CSDiagnosticInfo(ErrorCode.ERR_BindToBogus, this); } _typeCustomModifiers = CSharpCustomModifier.Convert(propertyParams[0].CustomModifiers); _refKind = propertyParams[0].IsByRef ? RefKind.Ref : RefKind.None; // CONSIDER: Can we make parameter type computation lazy? TypeSymbol originalPropertyType = propertyParams[0].Type; _propertyType = DynamicTypeDecoder.TransformType(originalPropertyType, _typeCustomModifiers.Length, handle, moduleSymbol); // Dynamify object type if necessary _propertyType = _propertyType.AsDynamicIfNoPia(_containingType); _propertyType = TupleTypeDecoder.DecodeTupleTypesIfApplicable(_propertyType, handle, moduleSymbol); // A property is bogus and must be accessed by calling its accessors directly if the // accessor signatures do not agree, both with each other and with the property, // or if it has parameters and is not an indexer or indexed property. bool callMethodsDirectly = !DoSignaturesMatch(module, metadataDecoder, propertyParams, _getMethod, getMethodParams, _setMethod, setMethodParams) || MustCallMethodsDirectlyCore(); if (!callMethodsDirectly) { if ((object)_getMethod != null) { _getMethod.SetAssociatedProperty(this, MethodKind.PropertyGet); } if ((object)_setMethod != null) { _setMethod.SetAssociatedProperty(this, MethodKind.PropertySet); } } if (callMethodsDirectly) { _flags |= Flags.CallMethodsDirectly; } if ((mdFlags & PropertyAttributes.SpecialName) != 0) { _flags |= Flags.IsSpecialName; } if ((mdFlags & PropertyAttributes.RTSpecialName) != 0) { _flags |= Flags.IsRuntimeSpecialName; } }