Skip to content

Commit

Permalink
[lang] Mark generated elements with @SarlElementType.
Browse files Browse the repository at this point in the history
Signed-off-by: Stéphane Galland <galland@arakhne.org>
  • Loading branch information
gallandarakhneorg committed Apr 29, 2017
1 parent d86d415 commit 75efec9
Show file tree
Hide file tree
Showing 42 changed files with 1,181 additions and 3 deletions.
@@ -0,0 +1,56 @@
/*
* $Id$
*
* SARL is an general-purpose agent programming language.
* More details on http://www.sarl.io
*
* Copyright (C) 2014-2017 the original authors or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package io.sarl.lang.annotation;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

/** Annotation for marking a JvmElement with the specific type of SARL element.
*
* <p>This annotation is attached to the JvmElements that represent SARL specific
* type declarations, e.g. agent, behavior, etc.
*
* <p>This annotation is usually used for simulating quickly the "A instanceof B",
* wheree A is a JvmElement (not an Xbase element), and B is a Xbase type.
*
* @author $Author: sgalland$
* @version $FullVersion$
* @mavengroupid $GroupId$
* @mavenartifactid $ArtifactId$
* @since 0.6
*/
@Target({ ElementType.TYPE })
@Retention(RetentionPolicy.RUNTIME)
public @interface SarlElementType {

/** Replies the SARL type.
*
* <p>The replies value is the ID of the ECore type, e.g.
* {@code SarlPackage::SARL_AGENT} and {@code SarlPackage::SARL_BEHAVIOR}.
*
* @return the SARL element type
*/
int value();

}
Expand Up @@ -89,6 +89,7 @@
import org.eclipse.xtext.common.types.JvmFormalParameter;
import org.eclipse.xtext.common.types.JvmGenericType;
import org.eclipse.xtext.common.types.JvmIdentifiableElement;
import org.eclipse.xtext.common.types.JvmIntAnnotationValue;
import org.eclipse.xtext.common.types.JvmOperation;
import org.eclipse.xtext.common.types.JvmParameterizedTypeReference;
import org.eclipse.xtext.common.types.JvmType;
Expand Down Expand Up @@ -141,6 +142,7 @@
import io.sarl.lang.annotation.FiredEvent;
import io.sarl.lang.annotation.ImportedCapacityFeature;
import io.sarl.lang.annotation.PerceptGuardEvaluator;
import io.sarl.lang.annotation.SarlElementType;
import io.sarl.lang.annotation.SarlSourceCode;
import io.sarl.lang.annotation.SarlSpecification;
import io.sarl.lang.annotation.SyntheticMember;
Expand Down Expand Up @@ -379,6 +381,41 @@ private JvmAnnotationReference addAnnotationSafe(JvmAnnotationTarget target, Cla
return null;
}

/** Add annotation safely.
*
* <p>This function creates an annotation reference. If the type for the annotation is not found;
* no annotation is added.
*
* @param target the receiver of the annotation.
* @param annotationType the type of the annotation.
* @param value the annotations value.
* @return the annotation reference or <code>null</code> if the annotation cannot be added.
*/
private JvmAnnotationReference addAnnotationSafe(JvmAnnotationTarget target, Class<?> annotationType, int value) {
assert target != null;
assert annotationType != null;
try {
final JvmAnnotationReference result = this.typesFactory.createJvmAnnotationReference();
final JvmType jvmType = this.typeReferences.findDeclaredType(annotationType, target);
if (jvmType == null) {
return null;
}
if (!(jvmType instanceof JvmAnnotationType)) {
return null;
}
result.setAnnotation((JvmAnnotationType) jvmType);
final JvmIntAnnotationValue annotationValue = this.typesFactory.createJvmIntAnnotationValue();
annotationValue.getValues().add(value);
result.getExplicitValues().add(annotationValue);
if (target.getAnnotations().add(result)) {
return result;
}
} catch (IllegalArgumentException exception) {
// Ignore
}
return null;
}

/** Create an annotation with classes as values.
*
* @param type - the type of the annotation.
Expand Down Expand Up @@ -851,6 +888,9 @@ protected void initialize(XtendClass source, JvmGenericType inferredJvmType) {

// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);
} finally {
closeContext(context);
}
Expand Down Expand Up @@ -881,17 +921,24 @@ protected void initialize(XtendInterface source, JvmGenericType inferredJvmType)
context.getInheritedOperationsToImplement(),
null,
this.sarlSignatureProvider);

// Standard OOP generation
super.initialize(source, inferredJvmType);

// Add SARL synthetic functions
appendSyntheticDefaultValuedParameterMethods(
source,
inferredJvmType,
context);

// Add the @FunctionalInterface
appendFunctionalInterfaceAnnotation(inferredJvmType);

// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);
} finally {
closeContext(context);
}
Expand Down Expand Up @@ -922,15 +969,21 @@ protected void initialize(XtendAnnotationType source, JvmAnnotationType inferred
context.getInheritedOperationsToImplement(),
null,
this.sarlSignatureProvider);

// Standard OOP generation
super.initialize(source, inferredJvmType);

// Add SARL synthetic functions
appendSyntheticDefaultValuedParameterMethods(
source,
inferredJvmType,
context);

// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);
} finally {
closeContext(context);
}
Expand Down Expand Up @@ -961,15 +1014,21 @@ protected void initialize(XtendEnum source, JvmEnumerationType inferredJvmType)
context.getInheritedOperationsToImplement(),
null,
this.sarlSignatureProvider);

// Standard OOP generation
super.initialize(source, inferredJvmType);

// Add SARL synthetic functions
appendSyntheticDefaultValuedParameterMethods(
source,
inferredJvmType,
context);

// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);
} finally {
closeContext(context);
}
Expand Down Expand Up @@ -1033,6 +1092,9 @@ protected void initialize(SarlAgent source, JvmGenericType inferredJvmType) {
// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);

// Resolving any name conflict with the generated JVM type
this.nameClashResolver.resolveNameClashes(inferredJvmType);
} finally {
Expand Down Expand Up @@ -1098,6 +1160,9 @@ protected void initialize(SarlBehavior source, JvmGenericType inferredJvmType) {
// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);

// Resolving any name conflict with the generated JVM type
this.nameClashResolver.resolveNameClashes(inferredJvmType);
} finally {
Expand Down Expand Up @@ -1166,6 +1231,9 @@ protected void initialize(SarlEvent source, JvmGenericType inferredJvmType) {
// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);

// Resolving any name conflict with the generated JVM type
this.nameClashResolver.resolveNameClashes(inferredJvmType);
} finally {
Expand Down Expand Up @@ -1232,6 +1300,9 @@ protected void initialize(SarlSkill source, JvmGenericType inferredJvmType) {
// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);

// Resolving any name conflict with the generated JVM type
this.nameClashResolver.resolveNameClashes(inferredJvmType);
} finally {
Expand Down Expand Up @@ -1287,6 +1358,9 @@ protected void initialize(SarlCapacity source, JvmGenericType inferredJvmType) {
// Add the specification version of SARL
appendSARLSpecificationVersion(context, source, inferredJvmType);

// Add the type of SARL Element
appendSARLElementType(source, inferredJvmType);

// Resolving any name conflict with the generated JVM type
this.nameClashResolver.resolveNameClashes(inferredJvmType);
} finally {
Expand Down Expand Up @@ -2786,11 +2860,10 @@ protected void appendCloneFunctionIfCloneable(GenerationContext context, XtendTy
}
}

/** Append the SARL specification version as a private field of the given container.
/** Append the SARL specification version as an annotation to the given container.
*
* <p>The added field may be used by any underground platform for determining what is
* <p>The added annotation may be used by any underground platform for determining what is
* the version of the SARL specification that was used for generating the container.
* The principle is inspired from the serialVersionUID from Java.
*
* @param context the current generation context.
* @param source the source object.
Expand All @@ -2801,6 +2874,18 @@ protected void appendSARLSpecificationVersion(GenerationContext context, XtendTy
addAnnotationSafe(target, SarlSpecification.class, SARLVersion.SPECIFICATION_RELEASE_VERSION_STRING);
}

/** Append the SARL element type as an annotation to the given container.
*
* <p>The added annotation may be used by any underground platform for determining what is
* the type of the SARL element without invoking the costly "instanceof" operations.
*
* @param source the source object.
* @param target the inferred JVM object.
*/
protected void appendSARLElementType(XtendTypeDeclaration source, JvmDeclaredType target) {
addAnnotationSafe(target, SarlElementType.class, source.eClass().getClassifierID());
}

/** Remove the type parameters from the given type.
*
* @param type the type.
Expand Down
Expand Up @@ -20,6 +20,7 @@
import org.junit.Test;

import io.sarl.lang.SARLVersion;
import io.sarl.lang.sarl.SarlPackage;
import io.sarl.lang.sarl.SarlScript;
import io.sarl.tests.api.AbstractSarlTest;

Expand Down Expand Up @@ -61,6 +62,7 @@ public void bug23() throws Exception {
@Test
public void myAgentSpawnedCompile() throws Exception {
final String expectedMyAgentSpawned = multilineString(
"import io.sarl.lang.annotation.SarlElementType;",
"import io.sarl.lang.annotation.SarlSpecification;",
"import io.sarl.lang.annotation.SyntheticMember;",
"import io.sarl.lang.core.Address;",
Expand All @@ -69,6 +71,7 @@ public void myAgentSpawnedCompile() throws Exception {
"import org.eclipse.xtext.xbase.lib.Pure;",
"",
"@SarlSpecification(\"" + SARLVersion.SPECIFICATION_RELEASE_VERSION_STRING + "\")",
"@SarlElementType(" + SarlPackage.SARL_EVENT + ")",
"@SuppressWarnings(\"all\")",
"public class MyAgentSpawned extends AgentSpawned {",
" public UUID titi;",
Expand Down
Expand Up @@ -31,6 +31,7 @@

import io.sarl.lang.SARLVersion;
import io.sarl.lang.actionprototype.ActionPrototype;
import io.sarl.lang.sarl.SarlPackage;
import io.sarl.tests.api.AbstractSarlTest;

/**
Expand Down Expand Up @@ -86,13 +87,15 @@ public void testCompiler() throws Exception {
"import io.sarl.lang.annotation.DefaultValue;",
"import io.sarl.lang.annotation.DefaultValueSource;",
"import io.sarl.lang.annotation.DefaultValueUse;",
"import io.sarl.lang.annotation.SarlElementType;",
"import io.sarl.lang.annotation.SarlSourceCode;",
"import io.sarl.lang.annotation.SarlSpecification;",
"import io.sarl.lang.annotation.SyntheticMember;",
"import io.sarl.lang.core.AgentTrait;",
"import io.sarl.lang.core.Capacity;",
"",
"@SarlSpecification(\"" + SARLVersion.SPECIFICATION_RELEASE_VERSION_STRING + "\")",
"@SarlElementType(" + SarlPackage.SARL_CAPACITY + ")",
"@SuppressWarnings(\"all\")",
"public interface PhysicEnvironment extends Capacity {",
" @DefaultValueSource",
Expand Down Expand Up @@ -247,13 +250,15 @@ public void testCompiler() throws Exception {
final String expectedStandardPhysicEnvironment = multilineString(
"import io.sarl.lang.annotation.DefaultValue;",
"import io.sarl.lang.annotation.DefaultValueSource;",
"import io.sarl.lang.annotation.SarlElementType;",
"import io.sarl.lang.annotation.SarlSourceCode;",
"import io.sarl.lang.annotation.SarlSpecification;",
"import io.sarl.lang.annotation.SyntheticMember;",
"import io.sarl.lang.core.Agent;",
"import io.sarl.lang.core.Skill;",
"",
"@SarlSpecification(\"" + SARLVersion.SPECIFICATION_RELEASE_VERSION_STRING + "\")",
"@SarlElementType(" + SarlPackage.SARL_SKILL + ")",
"@SuppressWarnings(\"all\")",
"public class StandardPhysicEnvironment extends Skill implements PhysicEnvironment {",
" @DefaultValueSource",
Expand Down
Expand Up @@ -23,6 +23,7 @@
import org.junit.runners.Suite.SuiteClasses;

import io.sarl.lang.SARLVersion;
import io.sarl.lang.sarl.SarlPackage;
import io.sarl.lang.sarl.SarlScript;
import io.sarl.tests.api.AbstractSarlTest;

Expand Down Expand Up @@ -65,13 +66,15 @@ public void testCompiler() throws Exception {
"import io.sarl.lang.annotation.DefaultValue;",
"import io.sarl.lang.annotation.DefaultValueSource;",
"import io.sarl.lang.annotation.DefaultValueUse;",
"import io.sarl.lang.annotation.SarlElementType;",
"import io.sarl.lang.annotation.SarlSourceCode;",
"import io.sarl.lang.annotation.SarlSpecification;",
"import io.sarl.lang.annotation.SyntheticMember;",
"import io.sarl.lang.core.AgentTrait;",
"import io.sarl.lang.core.Capacity;",
"",
"@SarlSpecification(\"" + SARLVersion.SPECIFICATION_RELEASE_VERSION_STRING + "\")",
"@SarlElementType(" + SarlPackage.SARL_CAPACITY + ")",
"@SuppressWarnings(\"all\")",
"public interface C1 extends Capacity {",
" @DefaultValueSource",
Expand Down

0 comments on commit 75efec9

Please sign in to comment.