private bool TryVarianceAdjustmentToGetAccessibleType(CSemanticChecker semanticChecker, AggregateDeclaration context, AggregateType typeSrc, out CType typeDst) { Debug.Assert(typeSrc != null); Debug.Assert(typeSrc.IsInterfaceType || typeSrc.IsDelegateType); typeDst = null; AggregateSymbol aggSym = typeSrc.OwningAggregate; AggregateType aggOpenType = aggSym.getThisType(); if (!semanticChecker.CheckTypeAccess(aggOpenType, context)) { // if the aggregate symbol itself is not accessible, then forget it, there is no // variance that will help us arrive at an accessible type. return(false); } TypeArray typeArgs = typeSrc.TypeArgsThis; TypeArray typeParams = aggOpenType.TypeArgsThis; CType[] newTypeArgsTemp = new CType[typeArgs.Count]; for (int i = 0; i < newTypeArgsTemp.Length; i++) { CType typeArg = typeArgs[i]; if (semanticChecker.CheckTypeAccess(typeArg, context)) { // we have an accessible argument, this position is not a problem. newTypeArgsTemp[i] = typeArg; continue; } if (!typeArg.IsReferenceType || !((TypeParameterType)typeParams[i]).Covariant) { // This guy is inaccessible, and we are not going to be able to vary him, so we need to fail. return(false); } newTypeArgsTemp[i] = GetBestAccessibleType(semanticChecker, context, typeArg); // now we either have a value type (which must be accessible due to the above // check, OR we have an inaccessible type (which must be a ref type). In either // case, the recursion worked out and we are OK to vary this argument. } TypeArray newTypeArgs = semanticChecker.getBSymmgr().AllocParams(typeArgs.Count, newTypeArgsTemp); CType intermediateType = GetAggregate(aggSym, typeSrc.OuterType, newTypeArgs); // All type arguments were varied successfully, which means now we must be accessible. But we could // have violated constraints. Let's check that out. if (!TypeBind.CheckConstraints(semanticChecker, errHandling: null, intermediateType, CheckConstraintsFlags.NoErrors)) { return(false); } typeDst = intermediateType; Debug.Assert(semanticChecker.CheckTypeAccess(typeDst, context)); return(true); }
private bool TryVarianceAdjustmentToGetAccessibleType(CSemanticChecker semanticChecker, BindingContext bindingContext, AggregateType typeSrc, out CType typeDst) { Debug.Assert(typeSrc != null); Debug.Assert(typeSrc.isInterfaceType() || typeSrc.isDelegateType()); typeDst = null; AggregateSymbol aggSym = typeSrc.GetOwningAggregate(); AggregateType aggOpenType = aggSym.getThisType(); if (!semanticChecker.CheckTypeAccess(aggOpenType, bindingContext.ContextForMemberLookup)) { // if the aggregate symbol itself is not accessible, then forget it, there is no // variance that will help us arrive at an accessible type. return(false); } TypeArray typeArgs = typeSrc.GetTypeArgsThis(); TypeArray typeParams = aggOpenType.GetTypeArgsThis(); CType[] newTypeArgsTemp = new CType[typeArgs.Count]; for (int i = 0; i < typeArgs.Count; i++) { if (semanticChecker.CheckTypeAccess(typeArgs[i], bindingContext.ContextForMemberLookup)) { // we have an accessible argument, this position is not a problem. newTypeArgsTemp[i] = typeArgs[i]; continue; } if (!typeArgs[i].IsRefType() || !((TypeParameterType)typeParams[i]).Covariant) { // This guy is inaccessible, and we are not going to be able to vary him, so we need to fail. return(false); } CType intermediateTypeArg; if (GetBestAccessibleType(semanticChecker, bindingContext, typeArgs[i], out intermediateTypeArg)) { // now we either have a value type (which must be accessible due to the above // check, OR we have an inaccessible type (which must be a ref type). In either // case, the recursion worked out and we are OK to vary this argument. newTypeArgsTemp[i] = intermediateTypeArg; continue; } else { Debug.Assert(false, "GetBestAccessibleType unexpectedly failed on a type that was used as a type parameter"); return(false); } } TypeArray newTypeArgs = semanticChecker.getBSymmgr().AllocParams(typeArgs.Count, newTypeArgsTemp); CType intermediateType = this.GetAggregate(aggSym, typeSrc.outerType, newTypeArgs); // All type arguments were varied successfully, which means now we must be accessible. But we could // have violated constraints. Let's check that out. if (!TypeBind.CheckConstraints(semanticChecker, null /*ErrorHandling*/, intermediateType, CheckConstraintsFlags.NoErrors)) { return(false); } typeDst = intermediateType; Debug.Assert(semanticChecker.CheckTypeAccess(typeDst, bindingContext.ContextForMemberLookup)); return(true); }
private bool TryVarianceAdjustmentToGetAccessibleType(CSemanticChecker semanticChecker, BindingContext bindingContext, AggregateType typeSrc, out CType typeDst) { Debug.Assert(typeSrc != null); Debug.Assert(typeSrc.isInterfaceType() || typeSrc.isDelegateType()); typeDst = null; AggregateSymbol aggSym = typeSrc.GetOwningAggregate(); AggregateType aggOpenType = aggSym.getThisType(); if (!semanticChecker.CheckTypeAccess(aggOpenType, bindingContext.ContextForMemberLookup())) { // if the aggregate symbol itself is not accessible, then forget it, there is no // variance that will help us arrive at an accessible type. return false; } TypeArray typeArgs = typeSrc.GetTypeArgsThis(); TypeArray typeParams = aggOpenType.GetTypeArgsThis(); CType[] newTypeArgsTemp = new CType[typeArgs.size]; for (int i = 0; i < typeArgs.size; i++) { if (semanticChecker.CheckTypeAccess(typeArgs.Item(i), bindingContext.ContextForMemberLookup())) { // we have an accessible argument, this position is not a problem. newTypeArgsTemp[i] = typeArgs.Item(i); continue; } if (!typeArgs.Item(i).IsRefType() || !typeParams.Item(i).AsTypeParameterType().Covariant) { // This guy is inaccessible, and we are not going to be able to vary him, so we need to fail. return false; } CType intermediateTypeArg; if (GetBestAccessibleType(semanticChecker, bindingContext, typeArgs.Item(i), out intermediateTypeArg)) { // now we either have a value type (which must be accessible due to the above // check, OR we have an inaccessible type (which must be a ref type). In either // case, the recursion worked out and we are OK to vary this argument. newTypeArgsTemp[i] = intermediateTypeArg; continue; } else { Debug.Assert(false, "GetBestAccessibleType unexpectedly failed on a type that was used as a type parameter"); return false; } } TypeArray newTypeArgs = semanticChecker.getBSymmgr().AllocParams(typeArgs.size, newTypeArgsTemp); CType intermediateType = this.GetAggregate(aggSym, typeSrc.outerType, newTypeArgs); // All type arguments were varied successfully, which means now we must be accessible. But we could // have violated constraints. Let's check that out. if (!TypeBind.CheckConstraints(semanticChecker, null/*ErrorHandling*/, intermediateType, CheckConstraintsFlags.NoErrors)) { return false; } typeDst = intermediateType; Debug.Assert(semanticChecker.CheckTypeAccess(typeDst, bindingContext.ContextForMemberLookup())); return true; }
private void Reset() { _controller = new RuntimeBinderController(); _semanticChecker = new LangCompiler(_controller, new NameManager()); BSYMMGR bsymmgr = _semanticChecker.getBSymmgr(); NameManager nameManager = _semanticChecker.GetNameManager(); InputFile infile = bsymmgr.GetMiscSymFactory().CreateMDInfile(nameManager.Lookup(""), (mdToken)0); infile.SetAssemblyID(bsymmgr.AidAlloc(infile)); infile.AddToAlias(KAID.kaidThisAssembly); infile.AddToAlias(KAID.kaidGlobal); _symbolTable = new SymbolTable( bsymmgr.GetSymbolTable(), bsymmgr.GetSymFactory(), nameManager, _semanticChecker.GetTypeManager(), bsymmgr, _semanticChecker, infile); _semanticChecker.getPredefTypes().Init(_semanticChecker.GetErrorContext(), _symbolTable); _semanticChecker.GetTypeManager().InitTypeFactory(_symbolTable); SymbolLoader.getPredefinedMembers().RuntimeBinderSymbolTable = _symbolTable; SymbolLoader.SetSymbolTable(_symbolTable); _exprFactory = new ExprFactory(_semanticChecker.GetSymbolLoader().GetGlobalSymbolContext()); _outputContext = new OutputContext(); _nameGenerator = new NameGenerator(); _bindingContext = BindingContext.CreateInstance( _semanticChecker, _exprFactory, _outputContext, _nameGenerator, false, true, false, false, false, false, 0); _binder = new ExpressionBinder(_bindingContext); }