Small Bug in pgstat display during recovery conflict resolution

Andres Freund <andres@anarazel.de>

From: Andres Freund <andres@anarazel.de>
To: Simon Riggs <simon@2ndquadrant.com>, pgsql-hackers@postgresql.org
Date: 2010-02-07T20:47:39Z
Lists: pgsql-hackers

Attachments

Hi Simon, Hi all,


if (!logged && (wait_s > 0 || wait_us > 500000))
{
        const char *oldactivitymsg;
        int                     len;

        oldactivitymsg = get_ps_display(&len);
        snprintf(waitactivitymsg, sizeof(waitactivitymsg),
                         "waiting for max_standby_delay (%u s)",
                         MaxStandbyDelay);
        set_ps_display(waitactivitymsg, false);
        if (len > 100)
                len = 100;
        memcpy(waitactivitymsg, oldactivitymsg, len);

        pgstat_report_waiting(true);

        logged = true;
}
..
if (logged)
{
        set_ps_display(waitactivitymsg, false);
        pgstat_report_waiting(false);
}

That doesnt work because get_ps_display returns the internal buffer. This 
leads to the situation that after conflict resolution the 
"waiting for max_standby_delay ..."
message is displayed until the next segment starts where its replaced
again by the 
"... recovering ..." line.

Additionally the old code may print unintialized memory if get_ps_display
 returns a string without a \0 terminator.

The attached patch fixes that.

Andres