Skip to content

Commit ff2cde1

Browse files
authored
Stack traces for all task execution (#7718)
1 parent 02521e1 commit ff2cde1

2 files changed

Lines changed: 39 additions & 30 deletions

File tree

src/enclave/enclave.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@
3232
#include "node/rpc/user_frontend.h"
3333
#include "rpc_map.h"
3434
#include "rpc_sessions.h"
35+
#include "tasks/worker.h"
3536

3637
#include <openssl/engine.h>
3738

@@ -390,7 +391,7 @@ namespace ccf
390391
size_t tasks_done = 0;
391392
while (task != nullptr)
392393
{
393-
task->do_task();
394+
ccf::tasks::try_do_task(*task);
394395
++tasks_done;
395396
if (tasks_done >= max_messages)
396397
{
@@ -427,7 +428,7 @@ namespace ccf
427428
auto task = job_board.wait_for_task(timeout);
428429
if (task != nullptr)
429430
{
430-
task->do_task();
431+
ccf::tasks::try_do_task(*task);
431432
}
432433
}
433434
}

src/tasks/worker.h

Lines changed: 36 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -13,11 +13,43 @@
1313

1414
namespace ccf::tasks
1515
{
16-
// Logs the error message and prints a demangled stacktrace to stderr.
17-
// Prefers the throw-point backtrace (captured via __cxa_throw interposition)
18-
// when available, otherwise falls back to a catch-point backtrace.
16+
// Logs the error message and a demangled throw-point stacktrace when
17+
// available.
1918
void dump_stacktrace(const std::string& msg);
2019

20+
// Executes a task with exception handling. On any exception, logs a
21+
// stacktrace and aborts (unless abort_on_throw is false).
22+
inline void try_do_task(BaseTask& task, bool abort_on_throw = true)
23+
{
24+
if (task.is_cancelled())
25+
{
26+
return;
27+
}
28+
29+
try
30+
{
31+
task.do_task();
32+
}
33+
catch (const std::exception& e)
34+
{
35+
dump_stacktrace(fmt::format(
36+
"{} task failed with exception: {}", task.get_name(), e.what()));
37+
if (abort_on_throw)
38+
{
39+
std::abort();
40+
}
41+
}
42+
catch (...)
43+
{
44+
dump_stacktrace(
45+
fmt::format("{} task failed with unknown exception", task.get_name()));
46+
if (abort_on_throw)
47+
{
48+
std::abort();
49+
}
50+
}
51+
}
52+
2153
inline void task_worker_loop(
2254
JobBoard& job_board,
2355
std::atomic<bool>& stop_signal,
@@ -30,31 +62,7 @@ namespace ccf::tasks
3062
auto task = job_board.wait_for_task(wait_time);
3163
if (task != nullptr)
3264
{
33-
if (!task->is_cancelled())
34-
{
35-
try
36-
{
37-
task->do_task();
38-
}
39-
catch (const std::exception& e)
40-
{
41-
dump_stacktrace(fmt::format(
42-
"{} task failed with exception: {}", task->get_name(), e.what()));
43-
if (abort_on_throw)
44-
{
45-
std::abort();
46-
}
47-
}
48-
catch (...)
49-
{
50-
dump_stacktrace(fmt::format(
51-
"{} task failed with unknown exception", task->get_name()));
52-
if (abort_on_throw)
53-
{
54-
std::abort();
55-
}
56-
}
57-
}
65+
try_do_task(*task, abort_on_throw);
5866
}
5967
}
6068
}

0 commit comments

Comments
 (0)