use of org.osate.aadl2.errormodel.PropagationGraph.PropagationPathEnd in project osate2 by osate.
the class AnalysisModel method impact.
public boolean impact(PropagationPathEnd src, PropagationPathEnd dst) {
for (PropagationPathRecord ppr : propagationPaths) {
if ((ppr.getPathSrc().getComponentInstance() == src.getComponentInstance()) && (ppr.getPathSrc().getErrorPropagation() == src.getErrorPropagation()) && (ppr.getPathDst().getComponentInstance() == dst.getComponentInstance()) && (ppr.getPathDst().getErrorPropagation() == dst.getErrorPropagation())) {
return true;
}
if ((ppr.getPathSrc().getComponentInstance() == src.getComponentInstance()) && (ppr.getPathSrc().getErrorPropagation() == src.getErrorPropagation())) {
ComponentInstance dstCI = ppr.getDstCI();
List<ErrorPropagation> eps = new ArrayList<ErrorPropagation>();
ComponentClassifier classifier = dstCI.getComponentClassifier();
eps.addAll(EMV2Util.getAllOutgoingErrorPropagations(classifier));
for (ErrorPropagation ep : eps) {
if (impact(new PropagationPathEnd(dstCI, ep), dst)) {
return true;
}
}
}
}
return false;
}
use of org.osate.aadl2.errormodel.PropagationGraph.PropagationPathEnd in project osate2 by osate.
the class AnalysisModel method getAllPropagationDestinationEnds.
/**
* return all feature (or for access component) instances that are the
* connection destination of the given feature instance The source and
* destinations are assumed to be components with error models
*
* @param fi
* @return list of ConnectionInstanceEnd
*/
public EList<ConnectionInstanceEnd> getAllPropagationDestinationEnds(ConnectionInstanceEnd fi) {
EList<ConnectionInstanceEnd> result = new BasicEList<ConnectionInstanceEnd>();
NamedElement f = null;
if (fi instanceof FeatureInstance) {
f = ((FeatureInstance) fi).getFeature();
} else {
f = ((ComponentInstance) fi).getSubcomponent();
}
for (PropagationPathRecord propagationPathRecord : propagationPaths) {
PropagationPathEnd src = propagationPathRecord.getPathSrc();
ErrorPropagation ep = src.getErrorPropagation();
Feature srcf = EMV2Util.getFeature(ep);
if (srcf != null && srcf == f) {
PropagationPathEnd dst = propagationPathRecord.pathDst;
ErrorPropagation dstep = dst.getErrorPropagation();
if (dstep != null) {
Feature dstf = EMV2Util.getFeature(dstep);
ComponentInstance dstCI = dst.getComponentInstance();
if (dstf != null) {
FeatureInstance dstfi = dstCI.findFeatureInstance(dstf);
result.add(dstfi);
} else if (EMV2Util.isAccess(dstep)) {
result.add(dstCI);
}
}
}
}
return result;
}
use of org.osate.aadl2.errormodel.PropagationGraph.PropagationPathEnd in project osate2 by osate.
the class PropagateErrorSources method startConnectionSourceFlows.
/**
* Start with the source of a connection instance
* @param ci component instance
*/
public void startConnectionSourceFlows(ComponentInstance root) {
Collection<ErrorSource> ceslist = EMV2Util.getAllConnectionErrorSources(root.getComponentClassifier());
if (ceslist.isEmpty()) {
return;
}
for (ErrorSource ces : ceslist) {
if (!Util.conditionHolds(ces, root)) {
continue;
}
EMSUtil.unsetAll(root.getSystemInstance());
// find connection instances that this connection is part of
String connName = ces.getSourceModelElement().getName();
ConnectionInstance conni = InstanceUtil.findConnectionInstance(root, (Connection) ces.getSourceModelElement());
EList<PropagationPathEnd> ends = Util.getAllPropagationDestinationEnds(faultModel, conni);
if (ends.size() == 0) {
return;
}
PropagationPathEnd ppe = ends.get(0);
ErrorPropagation destEP = ppe.getErrorPropagation();
ComponentInstance destci = ppe.getComponentInstance();
TypeSet fmType = ces.getFailureModeType();
String failuremodeDesc = ces.getFailureModeDescription();
TypeSet tsep = ces.getTypeTokenConstraint();
EList<TypeToken> result = tsep.getTypeTokens();
// XXX use this if we want all leaf types: EM2TypeSetUtil.generateAllLeafTypeTokens(tsep,EMV2Util.getContainingTypeUseContext(errorSource));
for (TypeToken typeToken : result) {
String failuremodeText;
if (failuremodeDesc == null) {
failuremodeText = generateOriginalFailureModeText(fmType != null ? fmType : typeToken);
} else {
failuremodeText = failuremodeDesc;
}
String effectText = generateOriginalFailureModeText(typeToken);
String connText = generateComponentPropagationPointText(destci, destEP);
traceErrorFlows(destci, destEP, typeToken, 0, "Connection " + connName + "," + failuremodeText + "," + effectText + " -> " + connText);
}
}
}
use of org.osate.aadl2.errormodel.PropagationGraph.PropagationPathEnd in project osate2 by osate.
the class PropagationGraphBackwardTraversal method traverseIncomingErrorPropagation.
/**
* traverse backwards according to propagation paths
* if preProcessing result is non-null return it instead of result of actual traversal (used for shared subtrees)
* handle external incoming propagations as origin by calling on processIncomingErrorPropagation
* handle source outgoing propagation
* collection of those results are post processed postProcessIncomingPropagation.
* If empty incoming propagation itself is processed as "leaf" by processIncomingErrorPropagation
* @param component component instance with incoming propagation
* @param errorPropagation incoming propagation
* @param type error type
* @return EObject (can be null)
*/
private EObject traverseIncomingErrorPropagation(ComponentInstance component, ErrorPropagation errorPropagation, TypeToken proptype, BigDecimal scale) {
List<EObject> results = new LinkedList<EObject>();
Collection<TypeToken> filteredtypes = filterTokenThroughConstraint(errorPropagation.getTypeSet(), proptype);
if (filteredtypes.isEmpty()) {
return null;
}
boolean traversed = false;
boolean hasCycle = false;
List<EObject> subResults = new LinkedList<EObject>();
for (TypeToken type : filteredtypes) {
boolean didProp = false;
// we want to track cycles.
// we do that by tagging the feature instance of the error propagation with the error type (as token)
ErrorModelState st = null;
FeatureInstance fi = EMV2Util.findFeatureInstance(errorPropagation, component);
if (fi != null) {
st = (ErrorModelState) ErrorModelStateAdapterFactory.INSTANCE.adapt(fi, ErrorModelState.class);
} else {
st = (ErrorModelState) ErrorModelStateAdapterFactory.INSTANCE.adapt(component, ErrorModelState.class);
}
if (st.visited(errorPropagation, type)) {
// we were there before.
hasCycle = true;
continue;
} else {
st.setVisitToken(errorPropagation, type);
}
EObject preResult = preProcessIncomingErrorPropagation(component, errorPropagation, type, scale);
if (preResult != null) {
// found common event
addSubresult(results, preResult);
continue;
}
for (PropagationGraphPath ppr : Util.getAllReversePropagationPaths(currentAnalysisModel, component, errorPropagation)) {
// traverse incoming
if (ppr.getConnection() != null) {
ErrorSource ces = EMV2Util.findConnectionErrorSourceForConnection(ppr.getConnection());
// the type constraint has to come from the error source as the connection does not have one
if (ces != null && contains(ces.getTypeTokenConstraint(), type)) {
// XXX filter type
EObject result = processConnectionErrorSource(ppr.getConnection(), ces, type, scale);
addSubresult(subResults, result);
didProp = true;
}
ComponentInstance contextCI = ppr.getConnection().getComponentInstance();
TypeTransformationSet tts = EMV2Util.getAllTypeTransformationSet(contextCI);
for (PropagationPathEnd ppe : Util.getAllPropagationSourceEnds(currentAnalysisModel, ppr.getConnection())) {
ComponentInstance componentSource = ppe.getComponentInstance();
ErrorPropagation propagationSource = ppe.getErrorPropagation();
TypeSet newtype = reverseMapTypeTokenToContributor(type, tts);
if (newtype != null) {
EList<TypeToken> ttlist = flattenTypesetElements(newtype);
for (TypeToken typeToken : ttlist) {
TypeToken ntype = EMV2TypeSetUtil.contains(typeToken, type) ? type : typeToken;
EObject result = traverseOutgoingErrorPropagation(componentSource, propagationSource, ntype, scale);
addSubresult(subResults, result);
didProp = true;
}
} else {
EObject result = traverseOutgoingErrorPropagation(componentSource, propagationSource, type, scale);
addSubresult(subResults, result);
didProp = true;
}
// source of connection
newtype = reverseMapTypeTokenToSource(type, tts);
if (newtype != null) {
EList<TypeToken> ttlist = flattenTypesetElements(newtype);
for (TypeToken typeToken : ttlist) {
TypeToken ntype = EMV2TypeSetUtil.contains(typeToken, type) ? type : typeToken;
EObject result = traverseOutgoingErrorPropagation(componentSource, propagationSource, ntype, scale);
addSubresult(subResults, result);
didProp = true;
}
} else {
EObject result = traverseOutgoingErrorPropagation(componentSource, propagationSource, type, scale);
if (!addSubresult(subResults, result)) {
didProp = true;
}
}
}
}
PropagationPathEnd ppe = ppr.getPathSrc();
ComponentInstance componentSource = ppe.getComponentInstance();
ErrorPropagation propagationSource = ppe.getErrorPropagation();
if (propagationSource.getDirection() == DirectionType.IN) {
// we have an external incoming propagation
EObject result = processIncomingErrorPropagation(componentSource, propagationSource, type, scale);
addSubresult(subResults, result);
didProp = true;
} else {
EObject result = traverseOutgoingErrorPropagation(componentSource, propagationSource, type, scale);
addSubresult(subResults, result);
didProp = true;
}
}
st.removeVisitedToken(errorPropagation, type);
if (didProp) {
traversed = true;
}
}
if (!subResults.isEmpty()) {
return postProcessIncomingErrorPropagation(component, errorPropagation, proptype, subResults, scale);
}
if (traversed || hasCycle) {
return null;
}
// we have no subresults and did not prune. Allow handling of incoming propagation as endpoint of traversal
return processIncomingErrorPropagation(component, errorPropagation, proptype, scale);
}
use of org.osate.aadl2.errormodel.PropagationGraph.PropagationPathEnd in project osate2 by osate.
the class PropagationGraphBackwardTraversal method traverseOutgoingErrorPropagation.
/**
* process an Outgoing Error Propagation by going backwards in the propagation graph
* if preProcessOutgoingerrorPropagation returns non-null return its value as traverse result.
* First we attempt to go backwards according to the component error behavior, i.e., the OutgoingPropagationCondition.
* If subresults is non-null then return value of postProcessingErrorPropagationCOndition.
* If not present we do it according to error flow specifications.
*
* @param component ComponentInstance
* @param errorPropagation outgoing ErrorPropagation
* @param type ErrorTypes
* @return EObject (can be null)
*/
public EObject traverseOutgoingErrorPropagation(final ComponentInstance component, final ErrorPropagation errorPropagation, TypeToken proptype, BigDecimal scale) {
List<EObject> subResults = new LinkedList<EObject>();
Collection<TypeToken> filteredTypes = filterTokenThroughConstraint(errorPropagation.getTypeSet(), proptype);
if (filteredTypes.isEmpty()) {
return null;
}
HashMultimap<ErrorPropagation, String> handledEOPs = HashMultimap.create();
boolean traverse = false;
boolean hasCycle = false;
for (TypeToken type : filteredTypes) {
// we did follow an OPC.
boolean didProp = false;
EObject found = preProcessOutgoingErrorPropagation(component, errorPropagation, type, scale);
if (found != null) {
addSubresult(subResults, found);
// found common event
continue;
}
// we want to track cycles.
// we do that by tagging the feature instance of the error propagation with the error type (as token)
ErrorModelState st = null;
FeatureInstance fi = EMV2Util.findFeatureInstance(errorPropagation, component);
if (fi != null) {
st = (ErrorModelState) ErrorModelStateAdapterFactory.INSTANCE.adapt(fi, ErrorModelState.class);
} else {
st = (ErrorModelState) ErrorModelStateAdapterFactory.INSTANCE.adapt(component, ErrorModelState.class);
}
if (st.visited(errorPropagation, type)) {
// we were there before.
hasCycle = true;
continue;
} else {
st.setVisitToken(errorPropagation, type);
}
// processing call has to be after the preproccessing call so it is not found and we proceed in processing.
// On the other hand it needs to be called here so the event exists in ftamodel and is found the next time around.
// Originally we were creating the events bottom up thus the loop did not find the event.
// EObject myEvent = processOutgoingErrorPropagation(component, errorPropagation, type, scale);
Collection<ErrorFlow> errorFlows = EMV2Util.getAllErrorFlows(component);
Collection<OutgoingPropagationCondition> opcs = EMV2Util.getAllOutgoingPropagationConditions(component);
for (OutgoingPropagationCondition opc : opcs) {
if ((opc.getTypeToken() != null && !isNoError(opc.getTypeToken())) || opc.getTypeToken() == null) {
if (opc.isAllPropagations() || (EMV2Util.isSame(opc.getOutgoing(), errorPropagation))) {
// opc token if OPC token is subtype or same type
Collection<TypeToken> opcFilteredTypes = filterTokenThroughConstraint(opc.getTypeToken(), type);
for (TypeToken opctype : opcFilteredTypes) {
if (contains(opc.getTypeToken(), opctype)) {
EObject res = handleOutgoingErrorPropagationCondition(component, opc, opctype, handledEOPs, scale);
addSubresult(subResults, res);
didProp = true;
}
}
}
}
}
// try to find a path from an outer to an inner out error propagation
EList<PropagationPathEnd> propagationSources = Util.getAllPropagationSourceEnds(currentAnalysisModel, component, errorPropagation);
for (PropagationPathEnd ppe : propagationSources) {
ComponentInstance componentSource = ppe.getComponentInstance();
ErrorPropagation propagationSource = ppe.getErrorPropagation();
if (propagationSource.getDirection() == DirectionType.OUT) {
Set<ErrorPropagation> eops = handledEOPs.keySet();
if (!containsEOP(eops, propagationSource)) {
// if not already handled by a opc
EObject res = traverseOutgoingErrorPropagation(componentSource, propagationSource, type, scale);
addSubresult(subResults, res);
didProp = true;
}
}
}
for (ErrorFlow ef : errorFlows) {
if (ef instanceof ErrorPath) {
ErrorPath ep = (ErrorPath) ef;
if (handledEOPs.containsEntry(ep.getIncoming(), EMV2Util.getPrintName(type))) {
// already handled by a opc
continue;
}
if (Util.conditionHolds(ef, component)) {
/**
* Make sure that the error type we are looking for is contained
* in the error types for the out propagation.
* This is a fix for the JMR/SAVI WBS model.
*/
if (ep.isAllOutgoing() || EMV2Util.isSame(ep.getOutgoing(), errorPropagation)) {
BigDecimal newscale = scale;
double pathprobability = EMV2Properties.getProbability(component, ep, type);
if (pathprobability > 0) {
newscale = scale.multiply(BigDecimal.valueOf((pathprobability)));
}
if (ep.getTargetToken() != null) {
Collection<TypeToken> mappedTypes = filterTokenThroughConstraint(ep.getTargetToken(), type);
for (TypeToken mappedtype : mappedTypes) {
// we have a type mapping
EList<TypeToken> result;
if (ep.getTypeTokenConstraint() != null) {
// get type from path constraint
result = mapTokenThroughConstraint(ep.getTypeTokenConstraint(), mappedtype);
} else {
// get incoming type from propagation
result = mapTokenThroughConstraint(ep.getIncoming().getTypeSet(), mappedtype);
}
for (TypeToken newToken : result) {
if (ep.isAllIncoming()) {
Collection<ErrorPropagation> inprops = EMV2Util.getAllIncomingErrorPropagations(component);
for (ErrorPropagation eprop : inprops) {
handledEOPs.put(eprop, EMV2Util.getPrintName(newToken));
EObject newEvent = traverseIncomingErrorPropagation(component, eprop, newToken, newscale);
addSubresult(subResults, newEvent);
didProp = true;
}
} else {
handledEOPs.put(ep.getIncoming(), EMV2Util.getPrintName(newToken));
EObject newEvent = traverseIncomingErrorPropagation(component, ep.getIncoming(), newToken, newscale);
addSubresult(subResults, newEvent);
didProp = true;
}
}
}
} else {
// no type mapping
if (ep.isAllIncoming()) {
Collection<ErrorPropagation> inprops = EMV2Util.getAllIncomingErrorPropagations(component);
for (ErrorPropagation eprop : inprops) {
TypeSet matchtype = ep.getTypeTokenConstraint();
if (matchtype == null) {
matchtype = eprop.getTypeSet();
}
EList<TypeToken> filteredtypes = filterTokenThroughConstraint(matchtype, type);
for (TypeToken subtype : filteredtypes) {
handledEOPs.put(eprop, EMV2Util.getPrintName(subtype));
EObject newEvent = traverseIncomingErrorPropagation(component, eprop, subtype, newscale);
addSubresult(subResults, newEvent);
didProp = true;
}
}
} else {
ErrorPropagation inep = ep.getIncoming();
TypeSet matchtype = ep.getTypeTokenConstraint();
if (matchtype == null) {
matchtype = inep.getTypeSet();
}
Collection<TypeToken> mappedtypes = filterTokenThroughConstraint(matchtype, type);
for (TypeToken subtype : mappedtypes) {
handledEOPs.put(inep, EMV2Util.getPrintName(subtype));
EObject newEvent = traverseIncomingErrorPropagation(component, inep, subtype, newscale);
addSubresult(subResults, newEvent);
didProp = true;
}
}
}
}
}
} else if (ef instanceof ErrorSource) {
ErrorSource errorSource = (ErrorSource) ef;
NamedElement src = errorSource.getSourceModelElement();
if (src instanceof ErrorPropagation) {
// check if error source was already handled by opc
ErrorPropagation srcep = (ErrorPropagation) src;
if (targetsEOP(opcs, srcep, type)) {
// already handled by a opc with the same target
continue;
}
}
if (Util.conditionHolds(ef, component)) {
if (errorSource.isAll() || EMV2Util.isSame(errorSource.getSourceModelElement(), errorPropagation)) {
Collection<TypeToken> mappedTypes = filterTokenThroughConstraint(errorSource.getTypeTokenConstraint(), type);
for (TypeToken mappedType : mappedTypes) {
if (src instanceof ErrorPropagation) {
handledEOPs.put((ErrorPropagation) src, EMV2Util.getPrintName(mappedType));
}
if (errorSource.getFailureModeReference() != null) {
List<EObject> stResults = new LinkedList<EObject>();
ErrorBehaviorState ebs = errorSource.getFailureModeReference();
EObject sEvent = traverseErrorBehaviorState(component, ebs, mappedType, scale);
addSubresult(stResults, sEvent);
EObject newEvent = postProcessErrorSource(component, errorSource, proptype, stResults, scale);
addSubresult(subResults, newEvent);
didProp = true;
} else {
EObject newEvent = processErrorSource(component, errorSource, mappedType, scale);
addSubresult(subResults, newEvent);
didProp = true;
}
}
}
}
}
}
st.removeVisitedToken(errorPropagation, type);
if (didProp) {
traverse = true;
}
}
if (!subResults.isEmpty()) {
// out propagation with sub elements
return postProcessOutgoingErrorPropagation(component, errorPropagation, proptype, subResults, scale);
}
if (hasCycle) {
return null;
}
if (traverse && !handledEOPs.isEmpty()) {
// we handled error out propagations
return null;
}
// out propagation as end point
return processOutgoingErrorPropagation(component, errorPropagation, proptype, scale);
}
Aggregations