aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/error-demo/error-demo.cc73
-rw-r--r--src/libutil/error.cc42
-rw-r--r--src/libutil/error.hh251
3 files changed, 204 insertions, 162 deletions
diff --git a/src/error-demo/error-demo.cc b/src/error-demo/error-demo.cc
index 8fb20d38c..fdb574b25 100644
--- a/src/error-demo/error-demo.cc
+++ b/src/error-demo/error-demo.cc
@@ -22,21 +22,25 @@ int main()
// created.
// ProgramError takes name, description, and an optional hint.
- printErrorInfo( ProgramError()
- .name("name")
- .description("error description")
- .nohint()
- );
+ printErrorInfo(
+ ErrorInfo::ProgramError("name",
+ "error description",
+ std::nullopt));
// ProgramWarning takes name, description, and an optional hint.
// The hint is in the form of a hintfmt class, which wraps boost::format(),
// and makes all the substituted text yellow.
- printErrorInfo( ProgramWarning()
- .name("warning name")
- .description("warning description")
- // the templated value, 'warning', is automatically colored yellow.
- .hint(hintfmt("there was a %1%", "warning"))
- );
+ printErrorInfo(
+ ErrorInfo::ProgramWarning("name",
+ "warning description",
+ std::optional(hintfmt("there was a %1%", "warning"))));
+
+ // printErrorInfo( ProgramWarning()
+ // .name("warning name")
+ // .description("warning description")
+ // // the templated value, 'warning', is automatically colored yellow.
+ // .hint(hintfmt("there was a %1%", "warning"))
+ // );
/*
// some invalid errors:
@@ -63,25 +67,34 @@ int main()
SymbolTable testTable;
auto problem_symbol = testTable.create("problem");
- printErrorInfo(NixLangWarning()
- .name("warning name")
- .description("warning description")
- .pos(Pos(problem_symbol, 40, 13))
- .linesOfCode(std::nullopt,
- "this is the problem line of code",
- std::nullopt)
- .hint(hintfmt("this hint has %1% templated %2%!!", "yellow" , "values")));
-
- // NixLangError is just the same as NixLangWarning, except for the Error
- // flag.
- printErrorInfo(NixLangError()
- .name("error name")
- .description("error description")
- .pos(Pos(problem_symbol, 40, 13))
- .linesOfCode(std::optional("previous line of code"),
- "this is the problem line of code",
- std::optional("next line of code"))
- .hint(hintfmt("this hint has %1% templated %2%!!", "yellow", "values")));
+ printErrorInfo(ErrorInfo::NixLangWarning(
+ "warning name",
+ "warning description",
+ Pos(problem_symbol, 40, 13),
+ std::nullopt,
+ "this is the problem line of code",
+ std::nullopt,
+ hintfmt("this hint has %1% templated %2%!!", "yellow", "values")));
+
+ // // NixLangError is just the same as NixLangWarning, except for the Error
+ // // flag.
+ // printErrorInfo(NixLangError()
+ // .name("error name")
+ // .description("error description")
+ // .pos(Pos(problem_symbol, 40, 13))
+ // .linesOfCode(std::optional("previous line of code"),
+ // "this is the problem line of code",
+ // std::optional("next line of code"))
+ // .hint(hintfmt("this hint has %1% templated %2%!!", "yellow", "values")));
+ printErrorInfo(ErrorInfo::NixLangError(
+ "error name",
+ "error description",
+ Pos(problem_symbol, 40, 13),
+ std::optional("previous line of code"),
+ "this is the problem line of code",
+ std::optional("next line of code"),
+ hintfmt("this hint has %1% templated %2%!!", "yellow", "values")));
+
return 0;
}
diff --git a/src/libutil/error.cc b/src/libutil/error.cc
index 8ab4a2dea..41fabbbcf 100644
--- a/src/libutil/error.cc
+++ b/src/libutil/error.cc
@@ -8,7 +8,43 @@ namespace nix
std::optional<string> ErrorInfo::programName = std::nullopt;
-string showErrLine(ErrLine &errLine)
+ErrorInfo ErrorInfo::ProgramError(const string &name,
+ const string &description,
+ const std::optional<hintformat> &hf)
+{
+ return ProgramEI(elError, name, description, hf);
+}
+
+ErrorInfo ErrorInfo::ProgramWarning(const string &name,
+ const string &description,
+ const std::optional<hintformat> &hf)
+{
+ return ProgramEI(elWarning, name, description, hf);
+}
+
+
+
+ErrorInfo ErrorInfo::ProgramEI(ErrLevel level,
+ const string &name,
+ const string &description,
+ const std::optional<hintformat> &hf)
+{
+ ErrorInfo ei(elError);
+ ei.name = name;
+ ei.description = description;
+ if (hf.has_value())
+ ei.hint = std::optional<string>(hf->str());
+ else
+ ei.hint = std::nullopt;
+ return ei;
+}
+
+
+
+
+
+
+string showErrLine(const ErrLine &errLine)
{
if (errLine.columnRange.has_value()) {
return (format("(%1%:%2%)") % errLine.lineNumber % errLine.columnRange->start).str();
@@ -17,7 +53,7 @@ string showErrLine(ErrLine &errLine)
};
}
-void printCodeLines(string &prefix, NixCode &nixCode)
+void printCodeLines(const string &prefix, const NixCode &nixCode)
{
if (nixCode.errLine.has_value()) {
@@ -69,7 +105,7 @@ void printCodeLines(string &prefix, NixCode &nixCode)
}
-void printErrorInfo(ErrorInfo &einfo)
+void printErrorInfo(const ErrorInfo &einfo)
{
int errwidth = 80;
string prefix = " ";
diff --git a/src/libutil/error.hh b/src/libutil/error.hh
index 57a9944be..a73b6639e 100644
--- a/src/libutil/error.hh
+++ b/src/libutil/error.hh
@@ -41,32 +41,61 @@ class NixCode
public:
std::optional<string> nixFile;
std::optional<ErrLine> errLine;
-
- ErrLine& ensureErrLine()
- {
- if (!this->errLine.has_value())
- this->errLine = std::optional(ErrLine());
- return *this->errLine;
- }
};
-// -------------------------------------------------
-// ErrorInfo.
+// ----------------------------------------------------------------
+// format for hints. same as fmt, except templated values
+// are always in yellow.
-// Forward friend class declarations. "builder classes"
template <class T>
-class AddName;
+class yellowify
+{
+public:
+ yellowify(T &s) : value(s) {}
+ T &value;
+};
template <class T>
-class AddDescription;
+std::ostream& operator<<(std::ostream &out, const yellowify<T> &y)
+{
+ return out << ANSI_YELLOW << y.value << ANSI_NORMAL;
+}
-template <class T>
-class AddPos;
+class hintformat
+{
+public:
+ hintformat(string format) :fmt(format)
+ {
+ fmt.exceptions(boost::io::all_error_bits ^ boost::io::too_many_args_bit);
+ }
+ template<class T>
+ hintformat& operator%(const T &value)
+ {
+ fmt % yellowify(value);
+ return *this;
+ }
-template <class T>
-class AddLOC;
+ std::string str() const
+ {
+ return fmt.str();
+ }
+
+ template <typename U>
+ friend class AddHint;
+private:
+ format fmt;
+};
+
+template<typename... Args>
+inline hintformat hintfmt(const std::string & fs, const Args & ... args)
+{
+ hintformat f(fs);
+ formatHelper(f, args...);
+ return f;
+}
-// The error info class itself.
+// -------------------------------------------------
+// ErrorInfo.
class ErrorInfo
{
public:
@@ -75,81 +104,94 @@ public:
string description;
std::optional<NixCode> nixCode;
std::optional<string> hint;
- ErrorInfo& GetEI()
- {
- return *this;
- }
static std::optional<string> programName;
- // give these access to the private constructor,
- // when they are direct descendants (children but not grandchildren).
- friend AddName<ErrorInfo>;
- friend AddDescription<ErrorInfo>;
- friend AddPos<ErrorInfo>;
- friend AddLOC<ErrorInfo>;
+ static ErrorInfo ProgramError(const string &name,
+ const string &description,
+ const std::optional<hintformat> &hf);
- NixCode& ensureNixCode()
- {
- if (!this->nixCode.has_value())
- this->nixCode = std::optional(NixCode());
- return *this->nixCode;
- }
-protected:
- // constructor is protected, so only the builder classes can create an ErrorInfo.
- ErrorInfo(ErrLevel level)
- {
- this->level = level;
- }
-};
-// Init as error
-class EIError : public ErrorInfo
-{
-protected:
- EIError() : ErrorInfo(elError) {}
-};
+ static ErrorInfo ProgramWarning(const string &name,
+ const string &description,
+ const std::optional<hintformat> &hf);
-// Init as warning
-class EIWarning : public ErrorInfo
-{
-protected:
- EIWarning() : ErrorInfo(elWarning) {}
-};
-// Builder class definitions.
-template <class T>
-class AddName : private T
-{
-public:
- T& name(const std::string &name)
+ template <class P>
+ static ErrorInfo NixLangError(const string &name,
+ const string &description,
+ const P &pos,
+ std::optional<string> prevloc,
+ string loc,
+ std::optional<string> nextloc,
+ const std::optional<hintformat> &hf)
{
- GetEI().name = name;
- return *this;
+ return NixLangEI(elError, name, description, pos, prevloc, loc, nextloc, hf);
}
-protected:
- ErrorInfo& GetEI()
+
+
+ template <class P>
+ static ErrorInfo NixLangWarning(const string &name,
+ const string &description,
+ const P &pos,
+ std::optional<string> prevloc,
+ string loc,
+ std::optional<string> nextloc,
+ const std::optional<hintformat> &hf)
{
- return T::GetEI();
+ return NixLangEI(elWarning, name, description, pos, prevloc, loc, nextloc, hf);
}
-};
-template <class T>
-class AddDescription : private T
-{
-public:
- T& description(const std::string &description)
+
+
+private:
+ template <class P>
+ static ErrorInfo NixLangEI(ErrLevel level,
+ const string &name,
+ const string &description,
+ const P &pos,
+ std::optional<string> prevloc,
+ string loc,
+ std::optional<string> nextloc,
+ const std::optional<hintformat> &hf)
{
- GetEI().description = description;
- return *this;
+ ErrorInfo ei(level);
+ ei.name = name;
+ ei.description = description;
+ if (hf.has_value())
+ ei.hint = std::optional<string>(hf->str());
+ else
+ ei.hint = std::nullopt;
+
+ ErrLine errline;
+ errline.lineNumber = pos.line;
+ errline.columnRange = { .start = pos.column, .len = 1 };
+ errline.prevLineOfCode = prevloc;
+ errline.errLineOfCode = loc;
+ errline.nextLineOfCode = nextloc;
+ NixCode nixcode;
+ nixcode.nixFile = pos.file;
+ nixcode.errLine = std::optional(errline);
+ ei.nixCode = std::optional(nixcode);
+
+ return ei;
}
-protected:
- ErrorInfo& GetEI()
+
+ static ErrorInfo ProgramEI(ErrLevel level,
+ const string &name,
+ const string &description,
+ const std::optional<hintformat> &hf);
+
+
+
+ // constructor is protected, so only the builder classes can create an ErrorInfo.
+ ErrorInfo(ErrLevel level)
{
- return T::GetEI();
+ this->level = level;
}
};
+/*
template <class T>
class AddPos : private T
{
@@ -186,60 +228,9 @@ protected:
return T::GetEI();
}
};
+*/
-
-// ----------------------------------------------------------------
-// format for hints. same as fmt, except templated values
-// are always in yellow.
-
-template <class T>
-class yellowify
-{
-public:
- yellowify(T &s) : value(s) {}
- T &value;
-};
-
-template <class T>
-std::ostream& operator<<(std::ostream &out, const yellowify<T> &y)
-{
- return out << ANSI_YELLOW << y.value << ANSI_NORMAL;
-}
-
-class hintformat
-{
-public:
- hintformat(string format) :fmt(format)
- {
- fmt.exceptions(boost::io::all_error_bits ^ boost::io::too_many_args_bit);
- }
- template<class T>
- hintformat& operator%(const T &value)
- {
- fmt % yellowify(value);
- return *this;
- }
-
- std::string str() const
- {
- return fmt.str();
- }
-
- template <typename U>
- friend class AddHint;
-private:
- format fmt;
-
-};
-
-template<typename... Args>
-inline hintformat hintfmt(const std::string & fs, const Args & ... args)
-{
- hintformat f(fs);
- formatHelper(f, args...);
- return f;
-}
-
+/*
// the template layer for adding a hint.
template <class T>
class AddHint : private T
@@ -261,11 +252,12 @@ protected:
return T::GetEI();
}
};
+*/
// --------------------------------------------------------
// error types
-typedef AddName<
+/*typedef AddName<
AddDescription<
AddHint<
EIError>>> ProgramError;
@@ -290,11 +282,12 @@ typedef AddName<
EIWarning>>>>> NixLangWarning;
+*/
// --------------------------------------------------------
// error printing
// just to cout for now.
-void printErrorInfo(ErrorInfo &einfo);
+void printErrorInfo(const ErrorInfo &einfo);
}