At Thu, 13 Dec 2018 11:33:39 +0100, Peter Eisentraut <peter.eisentraut@2ndquadrant.com> wrote in
<c170919d-c78b-3dac-5ff6-9bd12f7a38bc@2ndquadrant.com>
> This is a common pattern:
>
> PG_TRY();
> {
> ... code that might throw ereport(ERROR) ...
> }
> PG_CATCH();
> {
> cleanup();
> PG_RE_THROW();
> }
> PG_END_TRY();
> cleanup(); /* the same as above */
>
> I've played with a way to express this more compactly:
>
> PG_TRY();
> {
> ... code that might throw ereport(ERROR) ...
> }
> PG_FINALLY({
> cleanup();
> });
>
> See attached patch for how this works out in practice.
>
> Thoughts? Other ideas?
>
> One problem is that this currently makes pgindent crash. That's
> probably worth fixing anyway. Or perhaps find a way to write this
> differently.
Though I didn't look into individual change, this kind of
refactoring looks good to me. But the syntax looks
somewhat.. uh..
I'm not sure it is actually workable, but I suspect that what we
need here is just a shortcut of 'PG_CATCH();{PG_RE_THROW();}'.
Something like this:
#define PG_FINALLY() \
} \
else \
{ \
PG_exception_stack = save_exception_stack; \
error_context_stack = save_context_stack; \
PG_RE_THROW(); \
} \
PG_exception_stack = save_exception_stack; \
error_context_stack = save_context_stack; \
{
Which can be used as:
PG_TRY();
{
... code that might throw ereport(ERROR) ...
}
PG_FINALLY();
{
cleanup();
}
PG_TRY_END();
Or
#define PG_END_TRY_CATCHING_ALL() \
PG_FINALLY(); \
PG_END_TRY();
PG_TRY();
{
... code that might throw ereport(ERROR) ...
}
PG_END_TRY_CATCHING_ALL();
cleanup();
regards.
--
Kyotaro Horiguchi
NTT Open Source Software Center