NO_INLINE JsVar *jspeStatementFunctionDecl(bool isClass) {
  JsVar *funcName = 0;
  JsVar *funcVar;

#ifndef SAVE_ON_FLASH
  JSP_ASSERT_MATCH(isClass ? LEX_R_CLASS : LEX_R_FUNCTION);
#else
  JSP_ASSERT_MATCH(LEX_R_FUNCTION);
#endif

  bool actuallyCreateFunction = JSP_SHOULD_EXECUTE;
  if (actuallyCreateFunction) {
    funcName = jsvMakeIntoVariableName(jslGetTokenValueAsVar(lex), 0);
    if (!funcName) { // out of memory
      return 0;
    }
  }
  JSP_MATCH_WITH_CLEANUP_AND_RETURN(LEX_ID, jsvUnLock(funcName), 0);
#ifndef SAVE_ON_FLASH
  funcVar = isClass ? jspeClassDefinition(false) : jspeFunctionDefinition(false);
#else
  funcVar = jspeFunctionDefinition(false);
#endif
  if (actuallyCreateFunction) {
    // find a function with the same name (or make one)
    // OPT: can Find* use just a JsVar that is a 'name'?
    JsVar *existingName = jspeiFindNameOnTop(funcName, true);
    JsVar *existingFunc = jsvSkipName(existingName);
    if (jsvIsFunction(existingFunc)) {
      // 'proper' replace, that keeps the original function var and swaps the children
      funcVar = jsvSkipNameAndUnLock(funcVar);
      jswrap_function_replaceWith(existingFunc, funcVar);
    } else {
      jsvReplaceWith(existingName, funcVar);
    }
    jsvUnLock(funcName);
    funcName = existingName;
    jsvUnLock(existingFunc);
    // existingName is used - don't UnLock
  }
  jsvUnLock(funcVar);
  return funcName;
}
NO_INLINE JsVar *jspeStatementFunctionDecl(bool isClass) {
  JsVar *funcName = 0;
  JsVar *funcVar;

#ifndef SAVE_ON_FLASH
  JSP_ASSERT_MATCH(isClass ? LEX_R_CLASS : LEX_R_FUNCTION);
#else
  JSP_ASSERT_MATCH(LEX_R_FUNCTION);
#endif

  bool actuallyCreateFunction = JSP_SHOULD_EXECUTE;
  if (actuallyCreateFunction) {
    funcName = jsvMakeIntoVariableName(jslGetTokenValueAsVar(lex), 0);
    if (!funcName) {  
      return 0;
    }
  }
  JSP_MATCH_WITH_CLEANUP_AND_RETURN(LEX_ID, jsvUnLock(funcName), 0);
#ifndef SAVE_ON_FLASH
  funcVar = isClass ? jspeClassDefinition(false) : jspeFunctionDefinition(false);
#else
  funcVar = jspeFunctionDefinition(false);
#endif
  if (actuallyCreateFunction) {
     
     
    JsVar *existingName = jspeiFindNameOnTop(funcName, true);
    JsVar *existingFunc = jsvSkipName(existingName);
    if (jsvIsFunction(existingFunc)) {
       
      funcVar = jsvSkipNameAndUnLock(funcVar);
      jswrap_function_replaceWith(existingFunc, funcVar);
    } else {
      jsvReplaceWith(existingName, funcVar);
    }
    jsvUnLock(funcName);
    funcName = existingName;
    jsvUnLock(existingFunc);
     
  }
  jsvUnLock(funcVar);
  return funcName;
}