|
7 | 7 | * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
|
8 | 8 | * Portions Copyright (c) 1994, Regents of the University of California
|
9 | 9 | *
|
10 |
| - * $Header: /cvsroot/pgsql/src/backend/access/transam/xlog.c,v 1.85 2001/12/28 18:16:41 tgl Exp $ |
| 10 | + * $Header: /cvsroot/pgsql/src/backend/access/transam/xlog.c,v 1.86 2002/01/14 17:55:57 tgl Exp $ |
11 | 11 | *
|
12 | 12 | *-------------------------------------------------------------------------
|
13 | 13 | */
|
@@ -1262,15 +1262,40 @@ XLogFlush(XLogRecPtr record)
|
1262 | 1262 | WriteRqst.Write = WriteRqstPtr;
|
1263 | 1263 | WriteRqst.Flush = record;
|
1264 | 1264 | XLogWrite(WriteRqst);
|
1265 |
| - if (XLByteLT(LogwrtResult.Flush, record)) |
1266 |
| - elog(STOP, "XLogFlush: request %X/%X is not satisfied --- flushed only to %X/%X", |
1267 |
| - record.xlogid, record.xrecoff, |
1268 |
| - LogwrtResult.Flush.xlogid, LogwrtResult.Flush.xrecoff); |
1269 | 1265 | }
|
1270 | 1266 | LWLockRelease(WALWriteLock);
|
1271 | 1267 | }
|
1272 | 1268 |
|
1273 | 1269 | END_CRIT_SECTION();
|
| 1270 | + |
| 1271 | + /* |
| 1272 | + * If we still haven't flushed to the request point then we have a |
| 1273 | + * problem; most likely, the requested flush point is past end of XLOG. |
| 1274 | + * This has been seen to occur when a disk page has a corrupted LSN. |
| 1275 | + * |
| 1276 | + * Formerly we treated this as a STOP condition, but that hurts the |
| 1277 | + * system's robustness rather than helping it: we do not want to take |
| 1278 | + * down the whole system due to corruption on one data page. In |
| 1279 | + * particular, if the bad page is encountered again during recovery then |
| 1280 | + * we would be unable to restart the database at all! (This scenario |
| 1281 | + * has actually happened in the field several times with 7.1 releases. |
| 1282 | + * Note that we cannot get here while InRedo is true, but if the bad |
| 1283 | + * page is brought in and marked dirty during recovery then |
| 1284 | + * CreateCheckpoint will try to flush it at the end of recovery.) |
| 1285 | + * |
| 1286 | + * The current approach is to ERROR under normal conditions, but only |
| 1287 | + * NOTICE during recovery, so that the system can be brought up even if |
| 1288 | + * there's a corrupt LSN. Note that for calls from xact.c, the ERROR |
| 1289 | + * will be promoted to STOP since xact.c calls this routine inside a |
| 1290 | + * critical section. However, calls from bufmgr.c are not within |
| 1291 | + * critical sections and so we will not force a restart for a bad LSN |
| 1292 | + * on a data page. |
| 1293 | + */ |
| 1294 | + if (XLByteLT(LogwrtResult.Flush, record)) |
| 1295 | + elog(InRecovery ? NOTICE : ERROR, |
| 1296 | + "XLogFlush: request %X/%X is not satisfied --- flushed only to %X/%X", |
| 1297 | + record.xlogid, record.xrecoff, |
| 1298 | + LogwrtResult.Flush.xlogid, LogwrtResult.Flush.xrecoff); |
1274 | 1299 | }
|
1275 | 1300 |
|
1276 | 1301 | /*
|
|
0 commit comments