Codegen cg(0);
// FIXME: if the program is empty, we should we generate an empty %entry, or give an error?
- /*IR::Function *globalCode =*/ cg(program, &module);
+ /*IR::Function *globalCode =*/ cg(fileName, program, &module);
int (*exec)(void *) = outputType == LLVMOutputJit ? executeLLVMCode : 0;
return compileWithLLVM(&module, fileName, outputType, exec);
**
****************************************************************************/
+#include <QString>
#include "debugging.h"
#include <qmljs_environment.h>
#include <qmljs_objects.h>
namespace VM {
DiagnosticMessage::DiagnosticMessage()
- : fileName(0)
- , offset(0)
+ : offset(0)
, length(0)
, startLine(0)
, startColumn(0)
, type(0)
- , message(0)
, next(0)
{}
+DiagnosticMessage::~DiagnosticMessage()
+{
+ delete next;
+}
+
String *DiagnosticMessage::buildFullMessage(ExecutionContext *ctx) const
{
QString msg;
- if (fileName)
- msg = fileName->toQString() + QLatin1Char(':');
+ if (!fileName.isEmpty())
+ msg = fileName + QLatin1Char(':');
msg += QString::number(startLine) + QLatin1Char(':') + QString::number(startColumn) + QLatin1String(": ");
if (type == QQmlJS::VM::DiagnosticMessage::Error)
msg += QLatin1String("error");
else
msg += QLatin1String("warning");
- msg += ": " + message->toQString();
+ msg += ": " + message;
return ctx->engine->newString(msg);
}
{
enum { Error, Warning };
- String *fileName;
+ QString fileName;
quint32 offset;
quint32 length;
quint32 startLine;
unsigned startColumn: 31;
unsigned type: 1;
- String *message;
+ QString message;
DiagnosticMessage *next;
DiagnosticMessage();
+ ~DiagnosticMessage();
String *buildFullMessage(ExecutionContext *ctx) const;
};
VM::DiagnosticMessage *error = 0, **errIt = &error;
foreach (const QQmlJS::DiagnosticMessage &m, parser.diagnosticMessages()) {
if (m.isError()) {
- *errIt = new VM::DiagnosticMessage; // FIXME: should we ask the engine to create this object?
- (*errIt)->fileName = ctx->engine->newString(fileName);
+ *errIt = new VM::DiagnosticMessage;
+ (*errIt)->fileName = fileName;
(*errIt)->offset = m.loc.offset;
(*errIt)->length = m.loc.length;
(*errIt)->startLine = m.loc.startLine;
(*errIt)->startColumn = m.loc.startColumn;
(*errIt)->type = VM::DiagnosticMessage::Error;
- (*errIt)->message = ctx->engine->newString(m.message);
+ (*errIt)->message = m.message;
errIt = &(*errIt)->next;
} else {
std::cerr << qPrintable(fileName) << ':' << m.loc.startLine << ':' << m.loc.startColumn
}
Codegen cg(ctx);
- globalCode = cg(program, &module, mode);
+ globalCode = cg(fileName, program, &module, mode);
if (globalCode) {
// only generate other functions if global code generation succeeded.
foreach (IR::Function *function, module.functions) {
struct URIErrorPrototype;
struct String {
- String(const QString &text)
- : _text(text), _hashValue(0) {}
-
inline bool isEqualTo(const String *other) const {
if (this == other)
return true;
}
private:
+ friend struct StringPool;
+ String(const QString &text)
+ : _text(text), _hashValue(0) {}
+
+private:
QString _text;
mutable unsigned _hashValue;
};
struct SyntaxErrorObject: ErrorObject {
SyntaxErrorObject(ExecutionContext *ctx, DiagnosticMessage *msg);
+ ~SyntaxErrorObject() { delete msg; }
virtual QString className() { return QStringLiteral("SyntaxError"); }
virtual SyntaxErrorObject *asSyntaxError() { return this; }
{
}
-IR::Function *Codegen::operator()(Program *node, IR::Module *module, Mode mode)
+IR::Function *Codegen::operator()(const QString &fileName, Program *node, IR::Module *module, Mode mode)
{
assert(node);
+ _fileName = fileName;
_module = module;
_env = 0;
return globalCode;
}
-IR::Function *Codegen::operator()(AST::FunctionExpression *ast, IR::Module *module)
+IR::Function *Codegen::operator()(const QString &fileName, AST::FunctionExpression *ast, IR::Module *module)
{
+ _fileName = fileName;
_module = module;
_env = 0;
void Codegen::throwSyntaxError(const SourceLocation &loc, const QString &detail)
{
VM::DiagnosticMessage *msg = new VM::DiagnosticMessage;
+ msg->fileName = _fileName;
msg->offset = loc.begin();
msg->startLine = loc.startLine;
msg->startColumn = loc.startColumn;
- msg->message = new VM::String(detail);
+ msg->message = detail;
_context->throwSyntaxError(msg);
}
FunctionCode
};
- IR::Function *operator()(AST::Program *ast, IR::Module *module, Mode mode = GlobalCode);
- IR::Function *operator()(AST::FunctionExpression *ast, IR::Module *module);
+ IR::Function *operator()(const QString &fileName, AST::Program *ast, IR::Module *module, Mode mode = GlobalCode);
+ IR::Function *operator()(const QString &fileName, AST::FunctionExpression *ast, IR::Module *module);
protected:
enum Format { ex, cx, nx };
void throwSyntaxError(const AST::SourceLocation &loc, const QString &detail);
private:
+ QString _fileName;
Result _expr;
QString _property;
UiMember _uiMember;
IR::Module module;
Codegen cg(ctx);
- IR::Function *irf = cg(fe, &module);
+ IR::Function *irf = cg(QString(), fe, &module);
EvalInstructionSelection *isel = ctx->engine->iselFactory->create(ctx->engine);
isel->run(irf);
if (!o)
__qmljs_throw_type_error(ctx);
- String n(QString::fromLatin1("name"));
- Value name = o->__get__(ctx, &n);
+ Value name = o->__get__(ctx, ctx->engine->newString(QString::fromLatin1("name")));
QString qname;
if (name.isUndefined())
qname = QString::fromLatin1("Error");
else
qname = __qmljs_to_string(name, ctx).stringValue()->toQString();
- String m(QString::fromLatin1("message"));
- Value message = o->__get__(ctx, &m);
+ Value message = o->__get__(ctx, ctx->engine->newString(QString::fromLatin1("message")));
QString qmessage;
if (!message.isUndefined())
qmessage = __qmljs_to_string(message, ctx).stringValue()->toQString();