diff options
Diffstat (limited to 'src/textual.cc')
-rw-r--r-- | src/textual.cc | 88 |
1 files changed, 45 insertions, 43 deletions
diff --git a/src/textual.cc b/src/textual.cc index 8fbc5c08..04e90e45 100644 --- a/src/textual.cc +++ b/src/textual.cc @@ -1,5 +1,5 @@ /* - * Copyright (c) 2003-2018, John Wiegley. All rights reserved. + * Copyright (c) 2003-2019, John Wiegley. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are @@ -282,6 +282,10 @@ void instance_t::parse() std::cerr << _("Error: ") << err.what() << std::endl; context.errors++; + if (! current_context.empty()) + context.last = current_context + "\n" + err.what(); + else + context.last = err.what(); } } @@ -553,7 +557,7 @@ void instance_t::option_directive(char * line) void instance_t::automated_xact_directive(char * line) { - istream_pos_type pos = context.line_beg_pos; + std::istream::pos_type pos = context.line_beg_pos; bool reveal_context = true; @@ -649,7 +653,7 @@ void instance_t::automated_xact_directive(char * line) void instance_t::period_xact_directive(char * line) { - istream_pos_type pos = context.line_beg_pos; + std::istream::pos_type pos = context.line_beg_pos; bool reveal_context = true; @@ -739,17 +743,8 @@ void instance_t::include_directive(char * line) DEBUG("textual.include", "resolved path: " << filename.string()); mask_t glob; -#if BOOST_VERSION >= 103700 path parent_path = filename.parent_path(); -#if BOOST_VERSION >= 104600 glob.assign_glob('^' + filename.filename().string() + '$'); -#else - glob.assign_glob('^' + filename.filename() + '$'); -#endif -#else // BOOST_VERSION >= 103700 - path parent_path = filename.branch_path(); - glob.assign_glob('^' + filename.leaf() + '$'); -#endif // BOOST_VERSION >= 103700 bool files_found = false; if (exists(parent_path)) { @@ -757,21 +752,9 @@ void instance_t::include_directive(char * line) for (filesystem::directory_iterator iter(parent_path); iter != end; ++iter) { -#if BOOST_VERSION <= 103500 - if (is_regular(*iter)) -#else if (is_regular_file(*iter)) -#endif { -#if BOOST_VERSION >= 103700 -#if BOOST_VERSION >= 104600 string base = (*iter).path().filename().string(); -#else - string base = (*iter).filename(); -#endif -#else // BOOST_VERSION >= 103700 - string base = (*iter).leaf(); -#endif // BOOST_VERSION >= 103700 if (glob.match(base)) { journal_t * journal = context.journal; account_t * master = top_account(); @@ -912,8 +895,8 @@ void instance_t::end_apply_directive(char * kind) void instance_t::account_directive(char * line) { - istream_pos_type beg_pos = context.line_beg_pos; - std::size_t beg_linenum = context.linenum; + std::istream::pos_type beg_pos = context.line_beg_pos; + std::size_t beg_linenum = context.linenum; char * p = skip_ws(line); account_t * account = @@ -1644,29 +1627,30 @@ post_t * instance_t::parse_post(char * line, } DEBUG("textual.parse", "line " << context.linenum << ": " - << "POST assign: parsed amt = " << *post->assigned_amount); + << "POST assign: parsed balance amount = " << *post->assigned_amount); - amount_t& amt(*post->assigned_amount); + const amount_t& amt(*post->assigned_amount); value_t account_total (post->account->amount().strip_annotations(keep_details_t())); DEBUG("post.assign", "line " << context.linenum << ": " << "account balance = " << account_total); - DEBUG("post.assign", - "line " << context.linenum << ": " << "post amount = " << amt); + DEBUG("post.assign", "line " << context.linenum << ": " + << "post amount = " << amt << " (is_zero = " << amt.is_zero() << ")"); - amount_t diff = amt; + balance_t diff = amt; switch (account_total.type()) { case value_t::AMOUNT: - if (account_total.as_amount().commodity_ptr() == diff.commodity_ptr()) - diff -= account_total.as_amount(); + diff -= account_total.as_amount(); + DEBUG("textual.parse", "line " << context.linenum << ": " + << "Subtracting amount " << account_total.as_amount() << " from diff, yielding " << diff); break; case value_t::BALANCE: - if (optional<amount_t> comm_bal = - account_total.as_balance().commodity_amount(amt.commodity())) - diff -= *comm_bal; + diff -= account_total.as_balance(); + DEBUG("textual.parse", "line " << context.linenum << ": " + << "Subtracting balance " << account_total.as_balance() << " from diff, yielding " << diff); break; default: @@ -1680,18 +1664,34 @@ post_t * instance_t::parse_post(char * line, // Subtract amounts from previous posts to this account in the xact. for (post_t* p : xact->posts) { - if (p->account == post->account && - p->amount.commodity_ptr() == diff.commodity_ptr()) { + if (p->account == post->account) { diff -= p->amount; DEBUG("textual.parse", "line " << context.linenum << ": " - << "Subtract " << p->amount << ", diff = " << diff); + << "Subtracting " << p->amount << ", diff = " << diff); } } + // If amt has a commodity, restrict balancing to that. Otherwise, it's the blanket '0' and + // check that all of them are zero. + if (amt.has_commodity()) { + DEBUG("textual.parse", "line " << context.linenum << ": " + << "Finding commodity " << amt.commodity() << " (" << amt << ") in balance " << diff); + optional<amount_t> wanted_commodity = diff.commodity_amount(amt.commodity()); + if (!wanted_commodity) { + diff = amt - amt; // this is '0' with the correct commodity. + } else { + diff = *wanted_commodity; + } + DEBUG("textual.parse", "line " << context.linenum << ": " + << "Diff is now " << diff); + } + if (post->amount.is_null()) { // balance assignment if (! diff.is_zero()) { - post->amount = diff; + // This will fail if there are more than 1 commodity in diff, which is wanted, + // as amount cannot store more than 1 commodity. + post->amount = diff.to_amount(); DEBUG("textual.parse", "line " << context.linenum << ": " << "Overwrite null posting"); } @@ -1699,10 +1699,11 @@ post_t * instance_t::parse_post(char * line, // balance assertion diff -= post->amount; if (! no_assertions && ! diff.is_zero()) { - amount_t tot = amt - diff; + balance_t tot = -diff + amt; + DEBUG("textual.parse", "Balance assertion: off by " << diff << " (expected to see " << tot << ")"); throw_(parse_error, _f("Balance assertion off by %1% (expected to see %2%)") - % diff % tot); + % diff.to_string() % tot.to_string()); } } @@ -2012,7 +2013,8 @@ std::size_t journal_t::read_textual(parse_context_stack_t& context_stack) TRACE_FINISH(parsing_total, 1); if (context_stack.get_current().errors > 0) - throw error_count(context_stack.get_current().errors); + throw error_count(context_stack.get_current().errors, + context_stack.get_current().last); return context_stack.get_current().count; } |