uniformly check visibility of creator-methods via MethodModel._srcCtor
* reconstruct _srcCtor for binary bindings
* let ProblemReporter.invalidConstructor differentiate for different messages
  similar to invalidMethod (incl. one new IProblem)
* OTQualifiedAllocationExpression no longer needs to check this
See test621_accessToExternalizedRole3e and test621_accessToExternalizedRole3g
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/core/compiler/IProblem.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/core/compiler/IProblem.java
index 4dcc6f8..a8c8edb 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/core/compiler/IProblem.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/core/compiler/IProblem.java
@@ -1362,12 +1362,13 @@
 	int StaticRole                               = TEAM_RELATED + 2101; // 1.2.1
 	int IllegalModifierForRole                   = TEAM_RELATED + 2102; // 1.2.1(a)
 	int NotVisibleRoleMethod                     = TEAM_RELATED + 2103; // 1.2.1(e)
-	int DifferentTeamInstance 					 = TEAM_RELATED + 2104; // 1.2.1(e)
-	int NonPublicFieldOfExternalizedRole         = TEAM_RELATED + 2105; // 1.2.1(e)
-	int ExternalizedCallToNonPublicMethod		 = TEAM_RELATED + 2106; // 1.2.1(e)
-	int ExternalizedCallToNonPublicConstructor 	 = TEAM_RELATED + 2107; // 1.2.1(e)
-	int IndirectTSuperInvisible					 = TEAM_RELATED + 2108; // 1.2.1(e)
-	int RoleCantInitializeStaticField            = TEAM_RELATED + 2109; // 1.2.1(g)
+	int NotVisibleRoleConstructor 				 = TEAM_RELATED + 2104; // 1.2.1(e)
+	int DifferentTeamInstance 					 = TEAM_RELATED + 2105; // 1.2.1(e)
+	int NonPublicFieldOfExternalizedRole         = TEAM_RELATED + 2106; // 1.2.1(e)
+	int ExternalizedCallToNonPublicMethod		 = TEAM_RELATED + 2107; // 1.2.1(e)
+	int ExternalizedCallToNonPublicConstructor 	 = TEAM_RELATED + 2108; // 1.2.1(e)
+	int IndirectTSuperInvisible					 = TEAM_RELATED + 2109; // 1.2.1(e)
+	int RoleCantInitializeStaticField            = TEAM_RELATED + 2110; // 1.2.1(g)
 
 	int ExternalizingNonPublicRole               = TEAM_RELATED + 2200; // 1.2.2(a)
 	// unused: TEAM_RELATED + 2201
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/BinaryTypeBinding.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/BinaryTypeBinding.java
index 3d3eb5d..9de806b 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/BinaryTypeBinding.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/BinaryTypeBinding.java
@@ -40,6 +40,7 @@
 import org.eclipse.objectteams.otdt.internal.core.compiler.model.RoleModel;
 import org.eclipse.objectteams.otdt.internal.core.compiler.model.TeamModel;
 import org.eclipse.objectteams.otdt.internal.core.compiler.model.MethodModel.FakeKind;
+import org.eclipse.objectteams.otdt.internal.core.compiler.statemachine.copyinheritance.CopyInheritance;
 import org.eclipse.objectteams.otdt.internal.core.compiler.statemachine.transformer.TeamMethodGenerator;
 import org.eclipse.objectteams.otdt.internal.core.compiler.util.AstConverter;
 import org.eclipse.objectteams.otdt.internal.core.compiler.util.RoleTypeCreator;
@@ -792,9 +793,26 @@
 		result.modifiers &= ~ExtraCompilerModifiers.AccCallsBaseCtor;
 		MethodModel.setCallsBaseCtor(result);
 	}
-	// is it some other OT-generated method requiring to be marked as fake?
+	// handle various OT-specific methods:
 	char[] selector = method.getSelector();
 	if (CharOperation.prefixEquals(IOTConstants.OT_DOLLAR_NAME, selector)) {
+		// connect creation method to original constructor:
+		if (CopyInheritance.isCreator(result)) {
+			// extract the role name:
+			char[] roleName = ((ReferenceBinding) result.returnType).sourceName;
+			int dollarPos = CharOperation.lastIndexOf('$', roleName);
+			if (dollarPos > -1) // for unresolved bindings
+				roleName = CharOperation.subarray(roleName, dollarPos+1, -1);
+			// get the role class:
+			ReferenceBinding roleClass = getMemberType(CharOperation.concat(IOTConstants.OT_DELIM_NAME, roleName));
+			if (roleClass instanceof UnresolvedReferenceBinding)
+				roleClass = ((UnresolvedReferenceBinding)roleClass).resolve(this.environment, false);
+			// get and store the original ctor:
+			MethodBinding srcCtor = roleClass.getExactConstructor(result.parameters);
+			if (srcCtor != null)
+				MethodModel.getModel(result)._srcCtor = srcCtor;
+		}
+		// is it some other OT-generated method requiring to be marked as fake?
 		int secondDollar = CharOperation.indexOf('$', selector, 4, selector.length);
 		if (   secondDollar != -1
 			&& CharOperation.prefixEquals(AstConverter.PRIVATE, CharOperation.subarray(selector, secondDollar, -1)))
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/problem/ProblemReporter.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/problem/ProblemReporter.java
index 359d15a..c8dfefa 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/problem/ProblemReporter.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/problem/ProblemReporter.java
@@ -3107,6 +3107,17 @@
 			}
 			break;
 		case ProblemReasons.NotVisible :
+//{ObjectTeams: more specific message?
+		  if (shownConstructor.declaringClass.isRole()) {
+			if (   statement instanceof TSuperMessageSend
+				&& ((ReferenceBinding)((TSuperMessageSend)statement).actualReceiverType).getRealType() != shownConstructor.declaringClass.getRealType())
+				id = IProblem.IndirectTSuperInvisible;
+			else if (statement instanceof MessageSend && !((MessageSend)statement).receiver.isThis())
+				id= IProblem.ExternalizedCallToNonPublicConstructor;
+			else
+				id = IProblem.NotVisibleRoleConstructor;
+		  } else
+// SH}
 			if (insideDefaultConstructor){
 				id = IProblem.NotVisibleConstructorInDefaultConstructor;
 			} else if (insideImplicitConstructorCall){
@@ -8148,21 +8159,6 @@
         type.sourceStart(),
         type.sourceEnd());
 }
-public void externalizedCallToNonpublic(MethodBinding method, ReferenceBinding roleType, ASTNode location) {
-	String[] arguments = new String[] {
-			new String(roleType.readableName()),
-			new String(method.readableName())
-	};
-	String[] shortArguments = new String[] {
-			new String(roleType.shortReadableName()),
-			new String(method.shortReadableName())
-	};
-	this.handle(
-			method.isConstructor()? IProblem.ExternalizedCallToNonPublicConstructor : IProblem.ExternalizedCallToNonPublicMethod,
-			arguments, shortArguments,
-			location.sourceStart,
-			location.sourceEnd);
-}
 public void roleCantInitializeStaticField(FieldDeclaration fieldDecl)
 {
 	this.handle(IProblem.RoleCantInitializeStaticField,
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/problem/messages.properties b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/problem/messages.properties
index 1d3bb52..551cc75 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/problem/messages.properties
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/problem/messages.properties
@@ -641,12 +641,13 @@
 1102101 = Illegal modifier for role {0}. Roles cannot be static (OTJLD 1.2.1).
 1102102 = Illegal access modifier for role {0}. Only public and protected are allowed here (OTJLD 1.2.1(a)).
 1102103 = The method {1}({2}) from the role type {0} is not visible (OTJLD 1.2.1(e)).
-1102104 = Type mismatch: cannot convert from {0} to {1} because type anchors could not be proven to be the same instance (OTJLD 1.2.2(e)).
-1102105 = Cannot access non-public field {0} via externalized role {1} (OTJLD 1.2.1(e)).
-1102106 = Cannot access non-public method {1} via externalized role {0} (OTJLD 1.2.1(e)). 
-1102107 = Cannot access non-public constructor {1} to instantiate externalized role {0} (OTJLD 1.2.1(e)).
-1102108 = Indirect tsuper method inherited from {0} is not visible (OTJLD 1.2.1(e)).
-1102109 = Non-constant initialization not allowed for a static field of a role class (OTJLD 1.2.1(g)).
+1102104 = The role constructor {0}({1}) is not visible (OTJLD 1.2.1(e)).
+1102105 = Type mismatch: cannot convert from {0} to {1} because type anchors could not be proven to be the same instance (OTJLD 1.2.2(e)).
+1102106 = Cannot access non-public field {0} via externalized role {1} (OTJLD 1.2.1(e)).
+1102107 = Cannot access non-public method {1} via externalized role {0} (OTJLD 1.2.1(e)). 
+1102108 = Cannot access non-public constructor {0}({1}) to instantiate externalized role (OTJLD 1.2.1(e)).
+1102109 = Indirect tsuper method inherited from {0} is not visible (OTJLD 1.2.1(e)).
+1102110 = Non-constant initialization not allowed for a static field of a role class (OTJLD 1.2.1(g)).
 
 1102200 = Cannot externalize non-public role {0} (OTJLD 1.2.2(a)).
 #unused: 1102201 = 
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/objectteams/otdt/internal/core/compiler/ast/OTQualifiedAllocationExpression.java b/org.eclipse.jdt.core/compiler/org/eclipse/objectteams/otdt/internal/core/compiler/ast/OTQualifiedAllocationExpression.java
index c8377ca..819e4d4 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/objectteams/otdt/internal/core/compiler/ast/OTQualifiedAllocationExpression.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/objectteams/otdt/internal/core/compiler/ast/OTQualifiedAllocationExpression.java
@@ -212,8 +212,6 @@
 	        			MethodBinding ctor = role.getExactConstructor(creator.parameters);
 	        			if (Lifting.isLiftToConstructor(ctor, role))
 	        				scope.problemReporter().qualifiedUseOfLiftingConstructor(ctor, this.creatorCall);
-	        			if (RoleTypeBinding.isRoleWithExplicitAnchor(this.resolvedType) && !ctor.isPublic())
-	        				scope.problemReporter().externalizedCallToNonpublic(ctor, role, this);
 	        		}
 	        	}
 	        }