void Procedure::deprecatedWarning(const Token *callToken) { if (deprecated) { ecCharToCharStack(name, mn); if (documentationToken) { char *documentation = documentationToken->value.utf8CString(); compilerWarning(callToken, "%s is deprecated. Please refer to the documentation for further information:\n%s", mn, documentation); delete [] documentation; } else { compilerWarning(callToken, "%s is deprecated.", mn); } } }
Type Type::fetchRawType(EmojicodeChar name, EmojicodeChar enamespace, bool optional, const Token *token, bool *existent){ *existent = true; if(enamespace == globalNamespace){ switch (name) { case E_OK_HAND_SIGN: return Type(TT_BOOLEAN, optional); case E_INPUT_SYMBOL_FOR_SYMBOLS: return Type(TT_SYMBOL, optional); case E_STEAM_LOCOMOTIVE: return Type(TT_INTEGER, optional); case E_ROCKET: return Type(TT_DOUBLE, optional); case E_MEDIUM_WHITE_CIRCLE: if (optional) { compilerWarning(token, "🍬⚪️ is identical to ⚪️. Do not specify 🍬."); } return Type(TT_SOMETHING, false); case E_LARGE_BLUE_CIRCLE: return Type(TT_SOMEOBJECT, optional); case E_SPARKLES: compilerError(token, "The Nothingness type may not be referenced to."); } } Class *eclass = getClass(name, enamespace); if (eclass) { Type t = Type(eclass, optional); t.optional = optional; return t; } Protocol *protocol = getProtocol(name, enamespace); if(protocol){ return Type(protocol, optional); } Enum *eenum = getEnum(name, enamespace); if(eenum){ return Type(eenum, optional); } *existent = false; return typeNothingness; }
bool Package::fetchRawType(EmojicodeChar name, EmojicodeChar ns, bool optional, const Token *token, Type *type) { if (ns == globalNamespace) { switch (name) { case E_OK_HAND_SIGN: *type = Type(TT_BOOLEAN, optional); return true; case E_INPUT_SYMBOL_FOR_SYMBOLS: *type = Type(TT_SYMBOL, optional); return true; case E_STEAM_LOCOMOTIVE: *type = Type(TT_INTEGER, optional); return true; case E_ROCKET: *type = Type(TT_DOUBLE, optional); return true; case E_MEDIUM_WHITE_CIRCLE: if (optional) { compilerWarning(token, "🍬⚪️ is identical to ⚪️. Do not specify 🍬."); } *type = Type(TT_SOMETHING, false); return true; case E_LARGE_BLUE_CIRCLE: *type = Type(TT_SOMEOBJECT, optional); return true; case E_SPARKLES: compilerError(token, "The Nothingness type may not be referenced to."); } } std::array<EmojicodeChar, 2> key = {ns, name}; auto it = types_.find(key); if (it != types_.end()) { auto xtype = it->second; if (optional) xtype.setOptional(); *type = xtype; return true; } else { return false; } }
Type CommonTypeFinder::getCommonType(const Token *warningToken){ if(!firstTypeFound){ compilerWarning(warningToken, "Type is ambigious without more context."); } return commonType; }
void analyzeClass(Type classType, Writer &writer){ auto eclass = classType.eclass; writer.writeEmojicodeChar(eclass->name); if(eclass->superclass){ writer.writeUInt16(eclass->superclass->index); } else { //If the eclass does not have a superclass the own index gets written writer.writeUInt16(eclass->index); } Scope objectScope(true); //Get the ID offset for this eclass by summing up all superclasses instance variable counts uint16_t offset = 0; for(Class *aClass = eclass->superclass; aClass != nullptr; aClass = aClass->superclass){ offset += aClass->instanceVariables.size(); } writer.writeUInt16(eclass->instanceVariables.size() + offset); //Number of methods inclusive superclass writer.writeUInt16(eclass->nextMethodVti); //Number of eclass methods inclusive superclass writer.writeUInt16(eclass->nextClassMethodVti); //Initializer inclusive superclass writer.writeByte(eclass->inheritsContructors ? 1 : 0); writer.writeUInt16(eclass->nextInitializerVti); writer.writeUInt16(eclass->methodList.size()); writer.writeUInt16(eclass->initializerList.size()); writer.writeUInt16(eclass->classMethodList.size()); for (auto var : eclass->instanceVariables) { CompilerVariable *cv = new CompilerVariable(var->type, offset++, 1, false); cv->variable = var; objectScope.setLocalVariable(var->name, cv); } pushScope(&objectScope); for (auto method : eclass->methodList) { StaticFunctionAnalyzer::writeAndAnalyzeProcedure(*method, writer, classType); } for (auto initializer : eclass->initializerList) { StaticFunctionAnalyzer::writeAndAnalyzeProcedure(*initializer, writer, classType, false, initializer); } popScope(); for (auto classMethod : eclass->classMethodList) { StaticFunctionAnalyzer::writeAndAnalyzeProcedure(*classMethod, writer, classType, true); } if (eclass->instanceVariables.size() > 0 && eclass->initializerList.size() == 0) { auto str = classType.toString(typeNothingness, true); compilerWarning(eclass->classBegin, "Class %s defines %d instances variables but has no initializers.", str.c_str(), eclass->instanceVariables.size()); } writer.writeUInt16(eclass->protocols().size()); if (eclass->protocols().size() > 0) { auto biggestPlaceholder = writer.writePlaceholder<uint16_t>(); auto smallestPlaceholder = writer.writePlaceholder<uint16_t>(); uint_fast16_t smallestProtocolIndex = UINT_FAST16_MAX; uint_fast16_t biggestProtocolIndex = 0; for (auto protocol : eclass->protocols()) { writer.writeUInt16(protocol->index); if (protocol->index > biggestProtocolIndex) { biggestProtocolIndex = protocol->index; } if (protocol->index < smallestProtocolIndex) { smallestProtocolIndex = protocol->index; } writer.writeUInt16(protocol->methods().size()); for (auto method : protocol->methods()) { Method *clm = eclass->getMethod(method->name); if (clm == nullptr) { auto className = classType.toString(typeNothingness, true); auto protocolName = Type(protocol, false).toString(typeNothingness, true); ecCharToCharStack(method->name, ms); compilerError(eclass->classBegin, "Class %s does not agree to protocol %s: Method %s is missing.", className.c_str(), protocolName.c_str(), ms); } writer.writeUInt16(clm->vti); clm->checkPromises(method, "protocol definition", classType); } } biggestPlaceholder.write(biggestProtocolIndex); smallestPlaceholder.write(smallestProtocolIndex); } }