public MultiFileCompilationModuleGroup(TypeSystemContext context, IEnumerable<ModuleDesc> compilationModuleSet) : base(context) { _compilationModuleSet = new HashSet<ModuleDesc>(compilationModuleSet); // The fake assembly that holds compiler generated types is part of the compilation. _compilationModuleSet.Add(this.GeneratedAssembly); }
protected override void FinalizeRuntimeSpecificStaticFieldLayout(TypeSystemContext context, ref ComputedStaticFieldLayout layout) { // If the size of GCStatics is equal to the size set in PrepareRuntimeSpecificStaticFieldLayout, we // don't have any GC statics if (layout.GcStatics.Size == context.Target.PointerSize) { layout.GcStatics.Size = 0; } }
static public void Recycle(TypeSystemContext context) { // Only cache a reasonably small context that is still in Gen0 if (context.LoadFactor > 200 || GC.GetGeneration(context) > 0) return; // Flush the type system context from all types being recycled context.FlushTypeBuilderStates(); // No lock needed here - the reference assignment is atomic s_cachedContext.Target = context; }
private PInvokeILEmitter(MethodDesc targetMethod) { Debug.Assert(targetMethod.IsPInvoke); _targetMethod = targetMethod; _context = _targetMethod.Context; _importMetadata = targetMethod.GetPInvokeMethodMetadata(); _emitter = null; _marshallingCodeStream = null; _returnValueMarshallingCodeStream = null; _unmarshallingCodestream = null; }
public NoMetadataType(TypeSystemContext context, RuntimeTypeHandle genericTypeDefinition, DefType genericTypeDefinitionAsDefType, Instantiation instantiation, int hashcode) { _hashcode = hashcode; _context = context; _genericTypeDefinition = genericTypeDefinition; _genericTypeDefinitionAsDefType = genericTypeDefinitionAsDefType; if (_genericTypeDefinitionAsDefType == null) _genericTypeDefinitionAsDefType = this; _instantiation = instantiation; // Instantiation must either be: // Something valid (if the type is generic, or a generic type definition) // or Empty (if the type isn't a generic of any form) unsafe { Debug.Assert(((_instantiation.Length > 0) && _genericTypeDefinition.ToEETypePtr()->IsGenericTypeDefinition) || ((_instantiation.Length == 0) && !_genericTypeDefinition.ToEETypePtr()->IsGenericTypeDefinition)); } }
protected override void PrepareRuntimeSpecificStaticFieldLayout(TypeSystemContext context, ref ComputedStaticFieldLayout layout) { // GC statics start with a pointer to the "EEType" that signals the size and GCDesc to the GC layout.GcStatics.Size = context.Target.PointerSize; }
public RdXmlRootProvider(TypeSystemContext context, string rdXmlFileName) { _context = context; _documentRoot = XElement.Load(rdXmlFileName); }
public MultiFileLeafCompilationModuleGroup(TypeSystemContext context, IEnumerable<ModuleDesc> compilationModuleSet) : base(context, compilationModuleSet) { }
public ExplicitScopeAssembly(Cts.TypeSystemContext context, AssemblyName assemblyName) : base(context) { _assemblyName = assemblyName; }
public ModuleDesc(TypeSystemContext context) { Context = context; }
private static UnmanagedCallingConventions GetUnmanagedCallingConventionFromAttribute(CustomAttributeValue <TypeDesc> attributeWithCallConvsArray, TypeSystemContext context) { ImmutableArray <CustomAttributeTypedArgument <TypeDesc> > callConvArray = default; foreach (var arg in attributeWithCallConvsArray.NamedArguments) { if (arg.Name == "CallConvs") { callConvArray = (ImmutableArray <CustomAttributeTypedArgument <TypeDesc> >)arg.Value; } } UnmanagedCallingConventions result = 0; if (!callConvArray.IsDefault) { foreach (CustomAttributeTypedArgument <TypeDesc> type in callConvArray) { if (type.Value is not MetadataType mdType) { continue; } result = AccumulateCallingConventions(result, mdType); } } // If we haven't found a calling convention in the attribute, the calling convention is 'unmanaged'. if ((result & UnmanagedCallingConventions.CallingConventionMask) == 0) { result |= GetPlatformDefaultUnmanagedCallingConvention(context); } return(result); }
internal SignatureMethodVariable(TypeSystemContext context, int index) : base(context, index) { }
private static TypeDesc ConvertToCanon(TypeDesc typeToConvert, ref CanonicalFormKind kind) { TypeSystemContext context = typeToConvert.Context; if (kind == CanonicalFormKind.Universal) { return(context.UniversalCanonType); } else if (kind == CanonicalFormKind.Specific) { if (typeToConvert == context.UniversalCanonType) { kind = CanonicalFormKind.Universal; return(context.UniversalCanonType); } else if (typeToConvert.IsSignatureVariable) { return(typeToConvert); } else if (typeToConvert.IsDefType) { if (!typeToConvert.IsValueType) { return(context.CanonType); } else if (typeToConvert.HasInstantiation) { TypeDesc convertedType = typeToConvert.ConvertToCanonForm(CanonicalFormKind.Specific); if (convertedType.IsCanonicalSubtype(CanonicalFormKind.Universal)) { kind = CanonicalFormKind.Universal; return(context.UniversalCanonType); } return(convertedType); } else { return(typeToConvert); } } else if (typeToConvert.IsArray) { return(context.CanonType); } else { TypeDesc convertedType = typeToConvert.ConvertToCanonForm(CanonicalFormKind.Specific); if (convertedType.IsCanonicalSubtype(CanonicalFormKind.Universal)) { kind = CanonicalFormKind.Universal; return(context.UniversalCanonType); } return(convertedType); } } else { Debug.Assert(false); return(null); } }
public SingleFileCompilationModuleGroup(TypeSystemContext context) : base(context) { }
public static TypeDesc ConvertToCanon(TypeDesc typeToConvert, ref CanonicalFormKind kind) { TypeSystemContext context = typeToConvert.Context; if (kind == CanonicalFormKind.Universal) { return(context.UniversalCanonType); } else if (kind == CanonicalFormKind.Specific) { if (typeToConvert == context.UniversalCanonType) { kind = CanonicalFormKind.Universal; return(context.UniversalCanonType); } else if (typeToConvert.IsSignatureVariable) { return(typeToConvert); } else if (typeToConvert.IsDefType) { if (!typeToConvert.IsValueType) { return(context.CanonType); } else if (typeToConvert.HasInstantiation) { TypeDesc canonicalType = typeToConvert.ConvertToCanonForm(CanonicalFormKind.Specific); // This is a generic struct type. If the generic struct is instantiated over universal canon, // the entire struct becomes universally canonical. if (canonicalType.IsCanonicalSubtype(CanonicalFormKind.Universal)) { kind = CanonicalFormKind.Universal; return(context.UniversalCanonType); } return(canonicalType); } else if (typeToConvert.IsRuntimeDeterminedType) { // For non-universal canon cases, RuntimeDeterminedType's passed into this function are either // reference types (which are turned into normal Canon), or instantiated types (which are handled // by the above case.). But for UniversalCanon, we can have non-instantiated universal canon // which will reach this case. // We should only ever reach this for T__UniversalCanon. Debug.Assert(((RuntimeDeterminedType)typeToConvert).CanonicalType == context.UniversalCanonType); kind = CanonicalFormKind.Universal; return(context.UniversalCanonType); } else { return(typeToConvert); } } else if (typeToConvert.IsArray) { return(context.CanonType); } else { if (typeToConvert.IsCanonicalSubtype(CanonicalFormKind.Universal)) { kind = CanonicalFormKind.Universal; return(context.UniversalCanonType); } return(typeToConvert.ConvertToCanonForm(CanonicalFormKind.Specific)); } } else { Debug.Assert(false); return(null); } }
public override ComputedStaticFieldLayout ComputeStaticFieldLayout(DefType defType, StaticLayoutKind layoutKind) { MetadataType type = (MetadataType)defType; int numStaticFields = 0; foreach (var field in type.GetFields()) { if (!field.IsStatic || field.HasRva || field.IsLiteral) { continue; } numStaticFields++; } ComputedStaticFieldLayout result; result.GcStatics = new StaticsBlock(); result.NonGcStatics = new StaticsBlock(); result.ThreadGcStatics = new StaticsBlock(); result.ThreadNonGcStatics = new StaticsBlock(); if (numStaticFields == 0) { result.Offsets = Array.Empty <FieldAndOffset>(); return(result); } result.Offsets = new FieldAndOffset[numStaticFields]; TypeSystemContext context = type.Context; PrepareRuntimeSpecificStaticFieldLayout(context, ref result); int index = 0; foreach (var field in type.GetFields()) { // Nonstatic fields, literal fields, and RVA mapped fields don't participate in layout if (!field.IsStatic || field.HasRva || field.IsLiteral) { continue; } TypeDesc fieldType = field.FieldType; if (fieldType.IsByRef || (fieldType.IsValueType && ((DefType)fieldType).IsByRefLike)) { ThrowHelper.ThrowTypeLoadException(ExceptionStringID.ClassLoadGeneral, type); } ref StaticsBlock block = ref GetStaticsBlockForField(ref result, field); SizeAndAlignment sizeAndAlignment = ComputeFieldSizeAndAlignment(fieldType, context.Target.DefaultPackingSize, out bool _); block.Size = LayoutInt.AlignUp(block.Size, sizeAndAlignment.Alignment, context.Target); result.Offsets[index] = new FieldAndOffset(field, block.Size); block.Size = block.Size + sizeAndAlignment.Size; block.LargestAlignment = LayoutInt.Max(block.LargestAlignment, sizeAndAlignment.Alignment); index++; }
internal SignatureVariable(TypeSystemContext context, int index) { _context = context; _index = index; }
/// <summary> /// Called during static field layout to finish static block layout /// </summary> protected virtual void FinalizeRuntimeSpecificStaticFieldLayout(TypeSystemContext context, ref ComputedStaticFieldLayout layout) { }
public ModuleDesc(TypeSystemContext context, IAssemblyDesc assembly) { Context = context; Assembly = assembly; }
/// <summary> /// IF THESE SEMANTICS EVER CHANGE UPDATE THE LOGIC WHICH DEFINES THIS BEHAVIOR IN /// THE DYNAMIC TYPE LOADER AS WELL AS THE COMPILER. /// /// Parameter's are considered to have type layout dependent on their generic instantiation /// if the type of the parameter in its signature is a type variable, or if the type is a generic /// structure which meets 2 characteristics: /// 1. Structure size/layout is affected by the size/layout of one or more of its generic parameters /// 2. One or more of the generic parameters is a type variable, or a generic structure which also recursively /// would satisfy constraint 2. (Note, that in the recursion case, whether or not the structure is affected /// by the size/layout of its generic parameters is not investigated.) /// /// Examples parameter types, and behavior. /// /// T -> true /// List<T> -> false /// StructNotDependentOnArgsForSize<T> -> false /// GenStructDependencyOnArgsForSize<T> -> true /// StructNotDependentOnArgsForSize<GenStructDependencyOnArgsForSize<T>> -> true /// StructNotDependentOnArgsForSize<GenStructDependencyOnArgsForSize<List<T>>>> -> false /// /// Example non-parameter type behavior /// T -> true /// List<T> -> false /// StructNotDependentOnArgsForSize<T> -> *true* /// GenStructDependencyOnArgsForSize<T> -> true /// StructNotDependentOnArgsForSize<GenStructDependencyOnArgsForSize<T>> -> true /// StructNotDependentOnArgsForSize<GenStructDependencyOnArgsForSize<List<T>>>> -> false /// </summary> private bool TypeSignatureHasVarsNeedingCallingConventionConverter(ref NativeParser parser, TypeSystemContext context, HasVarsInvestigationLevel investigationLevel) { uint data; var kind = parser.GetTypeSignatureKind(out data); switch (kind) { case TypeSignatureKind.External: return false; case TypeSignatureKind.Variable: return true; case TypeSignatureKind.Lookback: { var lookbackParser = parser.GetLookbackParser(data); return TypeSignatureHasVarsNeedingCallingConventionConverter(ref lookbackParser, context, investigationLevel); } case TypeSignatureKind.Instantiation: { RuntimeTypeHandle genericTypeDef; if (!TryGetTypeFromSimpleTypeSignature(ref parser, out genericTypeDef)) { Debug.Assert(false); return true; // Returning true will prevent further reading from the native parser } if (!RuntimeAugments.IsValueType(genericTypeDef)) { // Reference types are treated like pointers. No calling convention conversion needed. Just consume the rest of the signature. for (uint i = 0; i < data; i++) TypeSignatureHasVarsNeedingCallingConventionConverter(ref parser, context, HasVarsInvestigationLevel.Ignore); return false; } else { bool result = false; for (uint i = 0; i < data; i++) result = TypeSignatureHasVarsNeedingCallingConventionConverter(ref parser, context, HasVarsInvestigationLevel.NotParameter) || result; if ((result == true) && (investigationLevel == HasVarsInvestigationLevel.Parameter)) { if (!TryComputeHasInstantiationDeterminedSize(genericTypeDef, context, out result)) Environment.FailFast("Unable to setup calling convention converter correctly"); return result; } return result; } } case TypeSignatureKind.Modifier: { // Arrays, pointers and byref types signatures are treated as pointers, not requiring calling convention conversion. // Just consume the parameter type from the stream and return false; TypeSignatureHasVarsNeedingCallingConventionConverter(ref parser, context, HasVarsInvestigationLevel.Ignore); return false; } case TypeSignatureKind.MultiDimArray: { // No need for a calling convention converter for this case. Just consume the signature from the stream. TypeSignatureHasVarsNeedingCallingConventionConverter(ref parser, context, HasVarsInvestigationLevel.Ignore); uint boundCount = parser.GetUnsigned(); for (uint i = 0; i < boundCount; i++) parser.GetUnsigned(); uint lowerBoundCount = parser.GetUnsigned(); for (uint i = 0; i < lowerBoundCount; i++) parser.GetUnsigned(); } return false; case TypeSignatureKind.FunctionPointer: { // No need for a calling convention converter for this case. Just consume the signature from the stream. uint argCount = parser.GetUnsigned(); for (uint i = 0; i < argCount; i++) TypeSignatureHasVarsNeedingCallingConventionConverter(ref parser, context, HasVarsInvestigationLevel.Ignore); } return false; default: parser.ThrowBadImageFormatException(); return true; } }
public CppCodegenCompilationRootProvider(TypeSystemContext context) { _context = context; }
public CanonType(TypeSystemContext context) : base(context) { Initialize(); }
public UniversalCanonType(TypeSystemContext context) : base(context) { Initialize(); }
public bool TryComputeHasInstantiationDeterminedSize(RuntimeTypeHandle typeHandle, TypeSystemContext context, out bool hasInstantiationDeterminedSize) { Debug.Assert(RuntimeAugments.IsGenericType(typeHandle) || RuntimeAugments.IsGenericTypeDefinition(typeHandle)); DefType type = (DefType)context.ResolveRuntimeTypeHandle(typeHandle); return TryComputeHasInstantiationDeterminedSize(type, out hasInstantiationDeterminedSize); }
public CanonBaseType(TypeSystemContext context) { _context = context; }
/// <summary> /// Returns JIT helper entrypoint. JIT helpers can be either implemented by entrypoint with given mangled name or /// by a method in class library. /// </summary> static public void GetEntryPoint(TypeSystemContext context, JitHelperId id, out string mangledName, out MethodDesc methodDesc) { mangledName = null; methodDesc = null; switch (id) { case JitHelperId.Throw: mangledName = "RhpThrowEx"; break; case JitHelperId.Rethrow: mangledName = "RhpRethrow"; break; case JitHelperId.Overflow: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowOverflowException"); break; case JitHelperId.RngChkFail: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowIndexOutOfRangeException"); break; case JitHelperId.FailFast: mangledName = "__fail_fast"; // TODO: Report stack buffer overrun break; case JitHelperId.ThrowNullRef: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowNullReferenceException"); break; case JitHelperId.ThrowDivZero: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowDivideByZeroException"); break; case JitHelperId.WriteBarrier: mangledName = "RhpAssignRef"; break; case JitHelperId.CheckedWriteBarrier: mangledName = "RhpCheckedAssignRef"; break; case JitHelperId.ByRefWriteBarrier: mangledName = "RhpByRefAssignRef"; break; case JitHelperId.NewMultiDimArr: mangledName = "RhNewMDArray"; break; case JitHelperId.Stelem_Ref: mangledName = "RhpStelemRef"; break; case JitHelperId.Ldelema_Ref: mangledName = "RhpLdelemaRef"; break; case JitHelperId.MemCpy: mangledName = "memcpy"; // TODO: Null reference handling break; case JitHelperId.MemSet: mangledName = "memset"; // TODO: Null reference handling break; case JitHelperId.GetRuntimeTypeHandle: // TODO: Reflection case JitHelperId.GetRuntimeMethodHandle: case JitHelperId.GetRuntimeFieldHandle: mangledName = "__fail_fast"; break; default: throw new NotImplementedException(id.ToString()); } }
/// <summary> /// Try to figure out field access information based on type metadata for native format types. /// </summary> /// <param name="metadataReader">Metadata reader for the declaring type</param> /// <param name="declaringTypeHandle">Declaring type for the method</param> /// <param name="fieldHandle">Field handle</param> /// <param name="canonFormKind">Canonical form to use</param> /// <param name="fieldAccessMetadata">Output - metadata information for field accessor construction</param> /// <returns>true when found, false otherwise</returns> private static bool TryGetFieldAccessMetadataFromNativeFormatMetadata( MetadataReader metadataReader, RuntimeTypeHandle declaringTypeHandle, FieldHandle fieldHandle, TypeSystemContext context, ref FieldAccessMetadata fieldAccessMetadata) { Field field = metadataReader.GetField(fieldHandle); string fieldName = metadataReader.GetString(field.Name); TypeDesc declaringType = context.ResolveRuntimeTypeHandle(declaringTypeHandle); #if SUPPORTS_NATIVE_METADATA_TYPE_LOADING if (declaringType is MetadataType) { return TryGetFieldAccessMetadataForNativeFormatType(declaringType, fieldName, ref fieldAccessMetadata); } #endif return false; }
private static UnmanagedCallingConventions GetPlatformDefaultUnmanagedCallingConvention(TypeSystemContext context) => context.Target.IsWindows ? UnmanagedCallingConventions.Stdcall : UnmanagedCallingConventions.Cdecl;
public SignatureVariableHashtable(TypeSystemContext context) { _context = context; }
public ILImporter(Compilation compilation, CppWriter writer, MethodDesc method, MethodIL methodIL) { _compilation = compilation; _nodeFactory = _compilation.NodeFactory; _writer = writer; _method = method; _methodSignature = method.Signature; _typeSystemContext = method.Context; if (!_methodSignature.IsStatic) _thisType = method.OwningType; _methodIL = methodIL; _ilBytes = _methodIL.GetILBytes(); _locals = _methodIL.GetLocals(); var ilExceptionRegions = _methodIL.GetExceptionRegions(); _exceptionRegions = new ExceptionRegion[ilExceptionRegions.Length]; for (int i = 0; i < ilExceptionRegions.Length; i++) { _exceptionRegions[i] = new ExceptionRegion() { ILRegion = ilExceptionRegions[i] }; } }
internal bool GetCallingConverterDataFromMethodSignature(TypeSystemContext context, RuntimeMethodSignature methodSig, NativeLayoutInfoLoadContext nativeLayoutContext, out bool hasThis, out TypeDesc[] parameters, out bool[] parametersWithGenericDependentLayout) { if (methodSig.IsNativeLayoutSignature) return GetCallingConverterDataFromMethodSignature_NativeLayout(context, methodSig.NativeLayoutSignature, nativeLayoutContext, out hasThis, out parameters, out parametersWithGenericDependentLayout); else { #if SUPPORTS_NATIVE_METADATA_TYPE_LOADING MetadataReader metadataReader = ModuleList.Instance.GetMetadataReaderForModule(methodSig.ModuleHandle); var methodHandle = methodSig.Token.AsHandle().ToMethodHandle(metadataReader); var metadataUnit = ((TypeLoaderTypeSystemContext)context).ResolveMetadataUnit(methodSig.ModuleHandle); var parser = new Internal.TypeSystem.NativeFormat.NativeFormatSignatureParser(metadataUnit, metadataReader.GetMethod(methodHandle).Signature, metadataReader); var signature = parser.ParseMethodSignature(); return GetCallingConverterDataFromMethodSignature_MethodSignature(signature, nativeLayoutContext, out hasThis, out parameters, out parametersWithGenericDependentLayout); #else parametersWithGenericDependentLayout = null; hasThis = false; parameters = null; return false; #endif } }
public MethodDesc ResolveTypeHandleAndMethodNameAndSigToVirtualMethodDesc(TypeSystemContext context, RuntimeTypeHandle declaringTypeHandle, MethodNameAndSignature methodNameAndSignature) { TypeDesc declaringType = context.ResolveRuntimeTypeHandle(declaringTypeHandle); MethodDesc targetVirtualMethod = null; foreach (MethodDesc m in declaringType.GetAllMethods()) { if (!m.IsVirtual) continue; if (m.NameAndSignature.Equals(methodNameAndSignature)) { targetVirtualMethod = m; } } return targetVirtualMethod; }
internal bool MethodSignatureHasVarsNeedingCallingConventionConverter(TypeSystemContext context, RuntimeMethodSignature methodSig) { if (methodSig.IsNativeLayoutSignature) return MethodSignatureHasVarsNeedingCallingConventionConverter_NativeLayout(context, methodSig.NativeLayoutSignature); else { #if SUPPORTS_NATIVE_METADATA_TYPE_LOADING MetadataReader metadataReader = ModuleList.Instance.GetMetadataReaderForModule(methodSig.ModuleHandle); var methodHandle = methodSig.Token.AsHandle().ToMethodHandle(metadataReader); var metadataUnit = ((TypeLoaderTypeSystemContext)context).ResolveMetadataUnit(methodSig.ModuleHandle); var parser = new Internal.TypeSystem.NativeFormat.NativeFormatSignatureParser(metadataUnit, metadataReader.GetMethod(methodHandle).Signature, metadataReader); var signature = parser.ParseMethodSignature(); return MethodSignatureHasVarsNeedingCallingConventionConverter_MethodSignature(signature); #else Environment.FailFast("Cannot parse signature"); return false; #endif } }
public ModuleToMetadataUnitHashtable(TypeSystemContext context) { _context = context; }
public CompilerGeneratedAssembly(TypeSystemContext context) : base(context, null) { _globalModuleType = new CompilerGeneratedType(this, "<Module>"); }
public ModuleToEcmaModuleHashtable(TypeSystemContext context) { _context = context; }
internal bool GetCallingConverterDataFromMethodSignature_NativeLayout(TypeSystemContext context, IntPtr methodSig, NativeLayoutInfoLoadContext nativeLayoutContext, out bool hasThis, out TypeDesc[] parameters, out bool[] parametersWithGenericDependentLayout) { hasThis = false; parameters = null; IntPtr moduleHandle = RuntimeAugments.GetModuleFromPointer(methodSig); NativeReader reader = GetNativeLayoutInfoReader(moduleHandle); NativeParser parser = new NativeParser(reader, reader.AddressToOffset(methodSig)); MethodCallingConvention callingConvention = (MethodCallingConvention)parser.GetUnsigned(); hasThis = !callingConvention.HasFlag(MethodCallingConvention.Static); uint numGenArgs = callingConvention.HasFlag(MethodCallingConvention.Generic) ? parser.GetUnsigned() : 0; uint parameterCount = parser.GetUnsigned(); parameters = new TypeDesc[parameterCount + 1]; parametersWithGenericDependentLayout = new bool[parameterCount + 1]; // One extra parameter to account for the return type for (uint i = 0; i <= parameterCount; i++) { // NativeParser is a struct, so it can be copied. NativeParser parserCopy = parser; // Parse the signature twice. The first time to find out the exact type of the signature // The second time to identify if the parameter loaded via the signature should be forced to be // passed byref as part of the universal generic calling convention. parameters[i] = GetConstructedTypeFromParserAndNativeLayoutContext(ref parser, nativeLayoutContext); parametersWithGenericDependentLayout[i] = TypeSignatureHasVarsNeedingCallingConventionConverter(ref parserCopy, context, HasVarsInvestigationLevel.Parameter); if (parameters[i] == null) return false; } return true; }
private bool MethodSignatureHasVarsNeedingCallingConventionConverter_NativeLayout(TypeSystemContext context, IntPtr methodSig) { IntPtr moduleHandle = RuntimeAugments.GetModuleFromPointer(methodSig); NativeReader reader = GetNativeLayoutInfoReader(moduleHandle); NativeParser parser = new NativeParser(reader, reader.AddressToOffset(methodSig)); MethodCallingConvention callingConvention = (MethodCallingConvention)parser.GetUnsigned(); uint numGenArgs = callingConvention.HasFlag(MethodCallingConvention.Generic) ? parser.GetUnsigned() : 0; uint parameterCount = parser.GetUnsigned(); // Check the return type of the method if (TypeSignatureHasVarsNeedingCallingConventionConverter(ref parser, context, HasVarsInvestigationLevel.Parameter)) return true; // Check the parameters of the method for (uint i = 0; i < parameterCount; i++) { if (TypeSignatureHasVarsNeedingCallingConventionConverter(ref parser, context, HasVarsInvestigationLevel.Parameter)) return true; } return false; }
private MetadataRecord HandleCustomAttributeConstantArray( Cts.ArrayType type, ImmutableArray <Ecma.CustomAttributeTypedArgument <Cts.TypeDesc> > value) { Cts.TypeDesc elementType = type.ElementType; if (elementType.IsEnum) { Cts.TypeSystemContext context = type.Context; return(new ConstantEnumArray { ElementType = HandleType(elementType), Value = HandleCustomAttributeConstantArray(context.GetArrayType(elementType.UnderlyingType), value), }); } switch (elementType.Category) { case Cts.TypeFlags.Boolean: return(new ConstantBooleanArray { Value = GetCustomAttributeConstantArrayElements <bool>(value) }); case Cts.TypeFlags.Byte: return(new ConstantByteArray { Value = GetCustomAttributeConstantArrayElements <byte>(value) }); case Cts.TypeFlags.Char: return(new ConstantCharArray { Value = GetCustomAttributeConstantArrayElements <char>(value) }); case Cts.TypeFlags.Double: return(new ConstantDoubleArray { Value = GetCustomAttributeConstantArrayElements <double>(value) }); case Cts.TypeFlags.Int16: return(new ConstantInt16Array { Value = GetCustomAttributeConstantArrayElements <short>(value) }); case Cts.TypeFlags.Int32: return(new ConstantInt32Array { Value = GetCustomAttributeConstantArrayElements <int>(value) }); case Cts.TypeFlags.Int64: return(new ConstantInt64Array { Value = GetCustomAttributeConstantArrayElements <long>(value) }); case Cts.TypeFlags.SByte: return(new ConstantSByteArray { Value = GetCustomAttributeConstantArrayElements <sbyte>(value) }); case Cts.TypeFlags.Single: return(new ConstantSingleArray { Value = GetCustomAttributeConstantArrayElements <float>(value) }); case Cts.TypeFlags.UInt16: return(new ConstantUInt16Array { Value = GetCustomAttributeConstantArrayElements <ushort>(value) }); case Cts.TypeFlags.UInt32: return(new ConstantUInt32Array { Value = GetCustomAttributeConstantArrayElements <uint>(value) }); case Cts.TypeFlags.UInt64: return(new ConstantUInt64Array { Value = GetCustomAttributeConstantArrayElements <ulong>(value) }); } if (elementType.IsString) { var record = new ConstantStringArray(); record.Value.Capacity = value.Length; foreach (var element in value) { MetadataRecord elementRecord = element.Value == null ? (MetadataRecord) new ConstantReferenceValue() : HandleString((string)element.Value); record.Value.Add(elementRecord); } return(record); } var result = new ConstantHandleArray(); result.Value.Capacity = value.Length; for (int i = 0; i < value.Length; i++) { MetadataRecord elementRecord = HandleCustomAttributeConstantValue(value[i].Type, value[i].Value); if (value[i].Type.IsEnum) { elementRecord = new ConstantBoxedEnumValue { Value = elementRecord, Type = HandleType(value[i].Type) }; } result.Value.Add(elementRecord); } return(result); }
private object TryParseNativeSignatureWorker(TypeSystemContext typeSystemContext, IntPtr moduleHandle, ref NativeParser parser, RuntimeTypeHandle[] typeGenericArgumentHandles, RuntimeTypeHandle[] methodGenericArgumentHandles, bool isMethodSignature) { Instantiation typeGenericArguments = typeSystemContext.ResolveRuntimeTypeHandles(typeGenericArgumentHandles ?? Array.Empty<RuntimeTypeHandle>()); Instantiation methodGenericArguments = typeSystemContext.ResolveRuntimeTypeHandles(methodGenericArgumentHandles ?? Array.Empty<RuntimeTypeHandle>()); NativeLayoutInfoLoadContext nativeLayoutContext = new NativeLayoutInfoLoadContext(); nativeLayoutContext._moduleHandle = moduleHandle; nativeLayoutContext._typeSystemContext = typeSystemContext; nativeLayoutContext._typeArgumentHandles = typeGenericArguments; nativeLayoutContext._methodArgumentHandles = methodGenericArguments; if (isMethodSignature) return nativeLayoutContext.GetMethod(ref parser); else return nativeLayoutContext.GetType(ref parser); }
// Parse a native layout info blob into a type / method given a signature pointer in the executable image private object TryParseNativeSignature(TypeSystemContext typeSystemContext, ref IntPtr signature, RuntimeTypeHandle[] typeGenericArgumentHandles, RuntimeTypeHandle[] methodGenericArgumentHandles, bool isMethodSignature) { IntPtr moduleHandle = RuntimeAugments.GetModuleFromPointer(signature); NativeReader reader = GetNativeLayoutInfoReader(moduleHandle); uint offset = reader.AddressToOffset(signature); NativeParser parser = new NativeParser(reader, offset); object retObject = TryParseNativeSignatureWorker(typeSystemContext, moduleHandle, ref parser, typeGenericArgumentHandles, methodGenericArgumentHandles, isMethodSignature); signature = reader.OffsetToAddress(parser.Offset); return retObject; }
/// <summary> /// Returns JIT helper entrypoint. JIT helpers can be either implemented by entrypoint with given mangled name or /// by a method in class library. /// </summary> static public void GetEntryPoint(TypeSystemContext context, JitHelperId id, out string mangledName, out MethodDesc methodDesc) { mangledName = null; methodDesc = null; switch (id) { case JitHelperId.Throw: mangledName = "RhpThrowEx"; break; case JitHelperId.Rethrow: mangledName = "RhRethrow"; break; case JitHelperId.Overflow: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowOverflowException"); break; case JitHelperId.RngChkFail: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowIndexOutOfRangeException"); break; case JitHelperId.FailFast: mangledName = "__fail_fast"; // TODO: Report stack buffer overrun break; case JitHelperId.ThrowNullRef: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowNullReferenceException"); break; case JitHelperId.ThrowDivZero: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowDivideByZeroException"); break; case JitHelperId.WriteBarrier: mangledName = "RhpAssignRef"; break; case JitHelperId.CheckedWriteBarrier: mangledName = "RhpCheckedAssignRef"; break; case JitHelperId.ByRefWriteBarrier: mangledName = "RhpByRefAssignRef"; break; case JitHelperId.Box: case JitHelperId.Box_Nullable: mangledName = "RhBox"; break; case JitHelperId.Unbox: mangledName = "RhUnbox2"; break; case JitHelperId.Unbox_Nullable: mangledName = "RhUnboxNullable"; break; case JitHelperId.NewMultiDimArr: mangledName = "RhNewMDArray"; break; case JitHelperId.Stelem_Ref: mangledName = "RhpStelemRef"; break; case JitHelperId.Ldelema_Ref: mangledName = "RhpLdelemaRef"; break; case JitHelperId.MemCpy: mangledName = "memcpy"; // TODO: Null reference handling break; case JitHelperId.MemSet: mangledName = "memset"; // TODO: Null reference handling break; case JitHelperId.GetRuntimeTypeHandle: methodDesc = context.GetHelperEntryPoint("LdTokenHelpers", "GetRuntimeTypeHandle"); break; case JitHelperId.GetRuntimeMethodHandle: // TODO: Reflection case JitHelperId.GetRuntimeFieldHandle: // TODO: Reflection mangledName = "__fail_fast"; break; case JitHelperId.Lng2Dbl: mangledName = "RhpLng2Dbl"; break; case JitHelperId.ULng2Dbl: mangledName = "RhpULng2Dbl"; break; case JitHelperId.Dbl2Lng: mangledName = "RhpDbl2Lng"; break; case JitHelperId.Dbl2ULng: mangledName = "RhpDbl2ULng"; break; case JitHelperId.Dbl2IntOvf: methodDesc = context.GetHelperEntryPoint("MathHelpers", "Dbl2IntOvf"); break; case JitHelperId.Dbl2LngOvf: methodDesc = context.GetHelperEntryPoint("MathHelpers", "Dbl2LngOvf"); break; case JitHelperId.Dbl2ULngOvf: methodDesc = context.GetHelperEntryPoint("MathHelpers", "Dbl2ULngOvf"); break; case JitHelperId.DblRem: mangledName = "RhpDblRem"; break; case JitHelperId.FltRem: mangledName = "RhpFltRem"; break; case JitHelperId.PInvokeBegin: mangledName = "RhpPInvoke"; break; case JitHelperId.PInvokeEnd: mangledName = "RhpPInvokeReturn"; break; case JitHelperId.ReversePInvokeEnter: mangledName = "RhpReversePInvoke2"; break; case JitHelperId.ReversePInvokeExit: mangledName = "RhpReversePInvokeReturn2"; break; default: throw new NotImplementedException(id.ToString()); } }
/// <summary> /// Returns JIT helper entrypoint. JIT helpers can be either implemented by entrypoint with given mangled name or /// by a method in class library. /// </summary> public static void GetEntryPoint(TypeSystemContext context, ReadyToRunHelper id, out string mangledName, out MethodDesc methodDesc) { mangledName = null; methodDesc = null; switch (id) { case ReadyToRunHelper.Throw: mangledName = "RhpThrowEx"; break; case ReadyToRunHelper.Rethrow: mangledName = "RhpRethrow"; break; case ReadyToRunHelper.Overflow: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowOverflowException"); break; case ReadyToRunHelper.RngChkFail: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowIndexOutOfRangeException"); break; case ReadyToRunHelper.FailFast: mangledName = "__fail_fast"; // TODO: Report stack buffer overrun break; case ReadyToRunHelper.ThrowNullRef: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowNullReferenceException"); break; case ReadyToRunHelper.ThrowDivZero: methodDesc = context.GetHelperEntryPoint("ThrowHelpers", "ThrowDivideByZeroException"); break; case ReadyToRunHelper.DebugBreak: mangledName = "RhDebugBreak"; break; case ReadyToRunHelper.WriteBarrier: mangledName = "RhpAssignRef"; break; case ReadyToRunHelper.CheckedWriteBarrier: mangledName = "RhpCheckedAssignRef"; break; case ReadyToRunHelper.ByRefWriteBarrier: mangledName = "RhpByRefAssignRef"; break; case ReadyToRunHelper.Box: case ReadyToRunHelper.Box_Nullable: mangledName = "RhBox"; break; case ReadyToRunHelper.Unbox: mangledName = "RhUnbox2"; break; case ReadyToRunHelper.Unbox_Nullable: mangledName = "RhUnboxNullable"; break; case ReadyToRunHelper.NewMultiDimArr_NonVarArg: methodDesc = context.GetHelperEntryPoint("ArrayHelpers", "NewObjArray"); break; case ReadyToRunHelper.NewArray: mangledName = "RhNewArray"; break; case ReadyToRunHelper.NewObject: mangledName = "RhNewObject"; break; case ReadyToRunHelper.Stelem_Ref: mangledName = "RhpStelemRef"; break; case ReadyToRunHelper.Ldelema_Ref: mangledName = "RhpLdelemaRef"; break; case ReadyToRunHelper.MemCpy: mangledName = "memcpy"; // TODO: Null reference handling break; case ReadyToRunHelper.MemSet: mangledName = "memset"; // TODO: Null reference handling break; case ReadyToRunHelper.GetRuntimeTypeHandle: methodDesc = context.GetHelperEntryPoint("LdTokenHelpers", "GetRuntimeTypeHandle"); break; case ReadyToRunHelper.GetRuntimeMethodHandle: // TODO: Reflection case ReadyToRunHelper.GetRuntimeFieldHandle: // TODO: Reflection mangledName = "__fail_fast"; break; case ReadyToRunHelper.Lng2Dbl: mangledName = "RhpLng2Dbl"; break; case ReadyToRunHelper.ULng2Dbl: mangledName = "RhpULng2Dbl"; break; case ReadyToRunHelper.Dbl2Lng: mangledName = "RhpDbl2Lng"; break; case ReadyToRunHelper.Dbl2ULng: mangledName = "RhpDbl2ULng"; break; case ReadyToRunHelper.Dbl2IntOvf: methodDesc = context.GetHelperEntryPoint("MathHelpers", "Dbl2IntOvf"); break; case ReadyToRunHelper.Dbl2UIntOvf: methodDesc = context.GetHelperEntryPoint("MathHelpers", "Dbl2UIntOvf"); break; case ReadyToRunHelper.Dbl2LngOvf: methodDesc = context.GetHelperEntryPoint("MathHelpers", "Dbl2LngOvf"); break; case ReadyToRunHelper.Dbl2ULngOvf: methodDesc = context.GetHelperEntryPoint("MathHelpers", "Dbl2ULngOvf"); break; case ReadyToRunHelper.DblRem: mangledName = "RhpDblRem"; break; case ReadyToRunHelper.FltRem: mangledName = "RhpFltRem"; break; case ReadyToRunHelper.PInvokeBegin: mangledName = "RhpPInvoke"; break; case ReadyToRunHelper.PInvokeEnd: mangledName = "RhpPInvokeReturn"; break; case ReadyToRunHelper.ReversePInvokeEnter: mangledName = "RhpReversePInvoke2"; break; case ReadyToRunHelper.ReversePInvokeExit: mangledName = "RhpReversePInvokeReturn2"; break; case ReadyToRunHelper.CheckCastAny: mangledName = "RhTypeCast_CheckCast2"; break; case ReadyToRunHelper.CheckInstanceAny: mangledName = "RhTypeCast_IsInstanceOf2"; break; case ReadyToRunHelper.MonitorEnter: methodDesc = context.GetHelperEntryPoint("SynchronizedMethodHelpers", "MonitorEnter"); break; case ReadyToRunHelper.MonitorExit: methodDesc = context.GetHelperEntryPoint("SynchronizedMethodHelpers", "MonitorExit"); break; case ReadyToRunHelper.MonitorEnterStatic: methodDesc = context.GetHelperEntryPoint("SynchronizedMethodHelpers", "MonitorEnterStatic"); break; case ReadyToRunHelper.MonitorExitStatic: methodDesc = context.GetHelperEntryPoint("SynchronizedMethodHelpers", "MonitorExitStatic"); break; default: throw new NotImplementedException(id.ToString()); } }