Bug 538748 - [Designer] [C Generator] Call to null function pointers of
state behaviors

Change-Id: I2c52e5cecbdfc208471bd5e0141c31b59fe33f8e
Signed-off-by: Shuai Li <shuai.li@cea.fr>
diff --git a/languages/c/org.eclipse.papyrus.designer.languages.c.codegen/src/org/eclipse/papyrus/designer/languages/c/codegen/lib/classScript.xtend b/languages/c/org.eclipse.papyrus.designer.languages.c.codegen/src/org/eclipse/papyrus/designer/languages/c/codegen/lib/classScript.xtend
index 1aa4728..29d85cb 100644
--- a/languages/c/org.eclipse.papyrus.designer.languages.c.codegen/src/org/eclipse/papyrus/designer/languages/c/codegen/lib/classScript.xtend
+++ b/languages/c/org.eclipse.papyrus.designer.languages.c.codegen/src/org/eclipse/papyrus/designer/languages/c/codegen/lib/classScript.xtend
@@ -101,42 +101,50 @@
 		
 		void «clazz.genName()»_init(«clazz.genName()»* self) {
 		
-		«IF (!clazz.ownedBehaviors.filter(StateMachine).isEmpty)»
-						//Default value initialization implementation
-						«FOR attribute : clazz.getAllAttributes»
-							«IF (attribute.defaultValue !== null && !attribute.isStatic && attribute.type !== null)»
-								«attribute.genInitDefaultValue»
-							«ENDIF»
-						«ENDFOR»
-		«ENDIF»
+			«IF (!clazz.ownedBehaviors.filter(StateMachine).isEmpty)»
+				//Default value initialization implementation
+				«FOR attribute : clazz.getAllAttributes»
+					«IF (attribute.defaultValue !== null && !attribute.isStatic && attribute.type !== null)»
+						«attribute.genInitDefaultValue»
+					«ENDIF»
+				«ENDFOR»
+			«ENDIF»
 		
-		«IF (!clazz.ownedBehaviors.filter(StateMachine).isEmpty)»
-			
+			«IF (!clazz.ownedBehaviors.filter(StateMachine).isEmpty)»
 				«var sm = clazz.ownedBehaviors.filter(StateMachine).head»
 				«var states =sm.regions.head.subvertices.filter(State).filter[!(it instanceof FinalState)]»
-					«IF !states.isEmpty»
-						// initialization of state internal behaviors if exists
-						«FOR s:states»
-							«IF TransformationUtil.isBehaviorExist(s.entry)»
-								self->states[«s.name»].entry= &«s.name»_entry;
-							«ENDIF»
-							«IF TransformationUtil.isBehaviorExist(s.exit)»
-								self->states[«s.name»].exit= &«s.name»_exit;
-							«ENDIF»
-							«IF TransformationUtil.isBehaviorExist(s.doActivity)»
-								self->states[«s.name»].doActivity= &«s.name»_doActivity;
-							«ENDIF»
-						«ENDFOR»
-			
-						«var initialState = TransformationUtil.findInitialState(clazz.ownedBehaviors.filter(StateMachine).head.regions.head)»
-						// set the activeStateID and call initial state entry and do Activity
-			
-							self->activeStateID = «initialState.name»;
-							self->states[«initialState.name»].entry();
-							self->states[«initialState.name»].doActivity();
-					«ENDIF»
+				«IF !states.isEmpty»
+					// initialization of state internal behaviors if exists
+					«FOR s:states»
+						«IF TransformationUtil.isBehaviorExist(s.entry)»
+							self->states[«s.name»].entry= &«s.name»_entry;
+						«ELSE»
+							self->states[«s.name»].entry= NULL;
+						«ENDIF»
+						«IF TransformationUtil.isBehaviorExist(s.exit)»
+							self->states[«s.name»].exit= &«s.name»_exit;
+						«ELSE»
+							self->states[«s.name»].exit= NULL;
+						«ENDIF»
+						«IF TransformationUtil.isBehaviorExist(s.doActivity)»
+							self->states[«s.name»].doActivity= &«s.name»_doActivity;
+						«ELSE»
+							self->states[«s.name»].doActivity= NULL;
+						«ENDIF»
+					«ENDFOR»
+
+					«var initialState = TransformationUtil.findInitialState(clazz.ownedBehaviors.filter(StateMachine).head.regions.head)»
+					// set the activeStateID and call initial state entry and do Activity
+					self->activeStateID = «initialState.name»;
+					if (self->states[«initialState.name»].entry != NULL) {
+						self->states[«initialState.name»].entry();
+					}
+					if (self->states[«initialState.name»].entry != NULL) {
+						self->states[«initialState.name»].doActivity();
+					}
+				«ENDIF»
 			«ENDIF»
-			}
+		}
 		«ENDIF»
 	'''
 
diff --git a/languages/c/org.eclipse.papyrus.designer.languages.c.codegen/src/org/eclipse/papyrus/designer/languages/c/codegen/lib/stateMachineScript.xtend b/languages/c/org.eclipse.papyrus.designer.languages.c.codegen/src/org/eclipse/papyrus/designer/languages/c/codegen/lib/stateMachineScript.xtend
index 7296abb..424eb63 100644
--- a/languages/c/org.eclipse.papyrus.designer.languages.c.codegen/src/org/eclipse/papyrus/designer/languages/c/codegen/lib/stateMachineScript.xtend
+++ b/languages/c/org.eclipse.papyrus.designer.languages.c.codegen/src/org/eclipse/papyrus/designer/languages/c/codegen/lib/stateMachineScript.xtend
@@ -113,24 +113,29 @@
 			/*  transition guard */

 			«IF !acslGuard.empty»«acslGuard»«ENDIF»

 			if («IF !cGuard.empty»«cGuard»«ELSE»1«ENDIF») {

-			/* exit Transition source */

-			self->states[«t.source.getName()»].exit();

-			

-			/* transition effect*/

-			«t.getTransitionEffect»

-			

-			/* update current state */

-			self->«ACTIVE_ROOT_STATE_ID» = «t.target.getName()» ;

-			

-			/* entry of the new state */

-			self->states[«t.target.getName()»].entry();

-			

-			/* doActivity of the new state */

-			self->states[«t.target.getName()»].doActivity();

-			

-			/* always call process completion event to handle completion transition */

-			ProcessCompletionEvent(self);

-

+				/* exit Transition source */

+				if (self->states[«t.source.getName()»].exit != NULL) {

+					self->states[«t.source.getName()»].exit();

+				}

+				

+				/* transition effect*/

+				«t.getTransitionEffect»

+				

+				/* update current state */

+				self->«ACTIVE_ROOT_STATE_ID» = «t.target.getName()» ;

+				

+				/* entry of the new state */

+				if (self->states[«t.target.getName()»].entry != NULL) {

+					self->states[«t.target.getName()»].entry();

+				}

+				

+				/* doActivity of the new state */

+				if (self->states[«t.target.getName()»].doActivity != NULL) {

+					self->states[«t.target.getName()»].doActivity();

+				}

+				

+				/* always call process completion event to handle completion transition */

+				ProcessCompletionEvent(self);

 			}'''

 		}

 		return ret