13
13
*
14
14
* Copyright (c) 2001-2008, PostgreSQL Global Development Group
15
15
*
16
- * $PostgreSQL: pgsql/src/backend/postmaster/pgstat.c,v 1.177 2008/08/01 13:16:08 alvherre Exp $
16
+ * $PostgreSQL: pgsql/src/backend/postmaster/pgstat.c,v 1.178 2008/08/05 12:09:30 mha Exp $
17
17
* ----------
18
18
*/
19
19
#include "postgres.h"
68
68
* Paths for the statistics files (relative to installation's $PGDATA).
69
69
* ----------
70
70
*/
71
- #define PGSTAT_STAT_FILENAME "global/pgstat.stat"
72
- #define PGSTAT_STAT_TMPFILE "global/pgstat.tmp"
71
+ #define PGSTAT_STAT_PERMANENT_FILENAME "global/pgstat.stat"
72
+ #define PGSTAT_STAT_PERMANENT_TMPFILE "global/pgstat.tmp"
73
+ #define PGSTAT_STAT_FILENAME "pg_stat_tmp/pgstat.stat"
74
+ #define PGSTAT_STAT_TMPFILE "pg_stat_tmp/pgstat.tmp"
73
75
74
76
/* ----------
75
77
* Timer definitions.
@@ -219,8 +221,8 @@ static void force_statwrite(SIGNAL_ARGS);
219
221
static void pgstat_beshutdown_hook (int code , Datum arg );
220
222
221
223
static PgStat_StatDBEntry * pgstat_get_db_entry (Oid databaseid , bool create );
222
- static void pgstat_write_statsfile (void );
223
- static HTAB * pgstat_read_statsfile (Oid onlydb );
224
+ static void pgstat_write_statsfile (bool permanent );
225
+ static HTAB * pgstat_read_statsfile (Oid onlydb , bool permanent );
224
226
static void backend_read_statsfile (void );
225
227
static void pgstat_read_current_status (void );
226
228
510
512
pgstat_reset_all (void )
511
513
{
512
514
unlink (PGSTAT_STAT_FILENAME );
515
+ unlink (PGSTAT_STAT_PERMANENT_FILENAME );
513
516
}
514
517
515
518
#ifdef EXEC_BACKEND
@@ -2598,7 +2601,7 @@ PgstatCollectorMain(int argc, char *argv[])
2598
2601
* zero.
2599
2602
*/
2600
2603
pgStatRunningInCollector = true;
2601
- pgStatDBHash = pgstat_read_statsfile (InvalidOid );
2604
+ pgStatDBHash = pgstat_read_statsfile (InvalidOid , true );
2602
2605
2603
2606
/*
2604
2607
* Setup the descriptor set for select(2). Since only one bit in the set
@@ -2638,7 +2641,7 @@ PgstatCollectorMain(int argc, char *argv[])
2638
2641
if (!PostmasterIsAlive (true))
2639
2642
break ;
2640
2643
2641
- pgstat_write_statsfile ();
2644
+ pgstat_write_statsfile (false );
2642
2645
need_statwrite = false;
2643
2646
need_timer = true;
2644
2647
}
@@ -2806,7 +2809,7 @@ PgstatCollectorMain(int argc, char *argv[])
2806
2809
/*
2807
2810
* Save the final stats to reuse at next startup.
2808
2811
*/
2809
- pgstat_write_statsfile ();
2812
+ pgstat_write_statsfile (true );
2810
2813
2811
2814
exit (0 );
2812
2815
}
@@ -2891,10 +2894,14 @@ pgstat_get_db_entry(Oid databaseid, bool create)
2891
2894
* pgstat_write_statsfile() -
2892
2895
*
2893
2896
* Tell the news.
2897
+ * If writing to the permanent file (happens when the collector is
2898
+ * shutting down only), remove the temporary file so that backends
2899
+ * starting up under a new postmaster can't read the old data before
2900
+ * the new collector is ready.
2894
2901
* ----------
2895
2902
*/
2896
2903
static void
2897
- pgstat_write_statsfile (void )
2904
+ pgstat_write_statsfile (bool permanent )
2898
2905
{
2899
2906
HASH_SEQ_STATUS hstat ;
2900
2907
HASH_SEQ_STATUS tstat ;
@@ -2904,17 +2911,19 @@ pgstat_write_statsfile(void)
2904
2911
PgStat_StatFuncEntry * funcentry ;
2905
2912
FILE * fpout ;
2906
2913
int32 format_id ;
2914
+ const char * tmpfile = permanent ?PGSTAT_STAT_PERMANENT_TMPFILE :PGSTAT_STAT_TMPFILE ;
2915
+ const char * statfile = permanent ?PGSTAT_STAT_PERMANENT_FILENAME :PGSTAT_STAT_FILENAME ;
2907
2916
2908
2917
/*
2909
2918
* Open the statistics temp file to write out the current values.
2910
2919
*/
2911
- fpout = fopen (PGSTAT_STAT_TMPFILE , PG_BINARY_W );
2920
+ fpout = fopen (tmpfile , PG_BINARY_W );
2912
2921
if (fpout == NULL )
2913
2922
{
2914
2923
ereport (LOG ,
2915
2924
(errcode_for_file_access (),
2916
2925
errmsg ("could not open temporary statistics file \"%s\": %m" ,
2917
- PGSTAT_STAT_TMPFILE )));
2926
+ tmpfile )));
2918
2927
return ;
2919
2928
}
2920
2929
@@ -2981,26 +2990,29 @@ pgstat_write_statsfile(void)
2981
2990
ereport (LOG ,
2982
2991
(errcode_for_file_access (),
2983
2992
errmsg ("could not write temporary statistics file \"%s\": %m" ,
2984
- PGSTAT_STAT_TMPFILE )));
2993
+ tmpfile )));
2985
2994
fclose (fpout );
2986
- unlink (PGSTAT_STAT_TMPFILE );
2995
+ unlink (tmpfile );
2987
2996
}
2988
2997
else if (fclose (fpout ) < 0 )
2989
2998
{
2990
2999
ereport (LOG ,
2991
3000
(errcode_for_file_access (),
2992
3001
errmsg ("could not close temporary statistics file \"%s\": %m" ,
2993
- PGSTAT_STAT_TMPFILE )));
2994
- unlink (PGSTAT_STAT_TMPFILE );
3002
+ tmpfile )));
3003
+ unlink (tmpfile );
2995
3004
}
2996
- else if (rename (PGSTAT_STAT_TMPFILE , PGSTAT_STAT_FILENAME ) < 0 )
3005
+ else if (rename (tmpfile , statfile ) < 0 )
2997
3006
{
2998
3007
ereport (LOG ,
2999
3008
(errcode_for_file_access (),
3000
3009
errmsg ("could not rename temporary statistics file \"%s\" to \"%s\": %m" ,
3001
- PGSTAT_STAT_TMPFILE , PGSTAT_STAT_FILENAME )));
3002
- unlink (PGSTAT_STAT_TMPFILE );
3010
+ tmpfile , statfile )));
3011
+ unlink (tmpfile );
3003
3012
}
3013
+
3014
+ if (permanent )
3015
+ unlink (PGSTAT_STAT_FILENAME );
3004
3016
}
3005
3017
3006
3018
@@ -3012,7 +3024,7 @@ pgstat_write_statsfile(void)
3012
3024
* ----------
3013
3025
*/
3014
3026
static HTAB *
3015
- pgstat_read_statsfile (Oid onlydb )
3027
+ pgstat_read_statsfile (Oid onlydb , bool permanent )
3016
3028
{
3017
3029
PgStat_StatDBEntry * dbentry ;
3018
3030
PgStat_StatDBEntry dbbuf ;
@@ -3027,6 +3039,7 @@ pgstat_read_statsfile(Oid onlydb)
3027
3039
FILE * fpin ;
3028
3040
int32 format_id ;
3029
3041
bool found ;
3042
+ const char * statfile = permanent ?PGSTAT_STAT_PERMANENT_FILENAME :PGSTAT_STAT_FILENAME ;
3030
3043
3031
3044
/*
3032
3045
* The tables will live in pgStatLocalContext.
@@ -3055,7 +3068,7 @@ pgstat_read_statsfile(Oid onlydb)
3055
3068
* return zero for anything and the collector simply starts from scratch
3056
3069
* with empty counters.
3057
3070
*/
3058
- if ((fpin = AllocateFile (PGSTAT_STAT_FILENAME , PG_BINARY_R )) == NULL )
3071
+ if ((fpin = AllocateFile (statfile , PG_BINARY_R )) == NULL )
3059
3072
return dbhash ;
3060
3073
3061
3074
/*
@@ -3244,6 +3257,9 @@ pgstat_read_statsfile(Oid onlydb)
3244
3257
done :
3245
3258
FreeFile (fpin );
3246
3259
3260
+ if (permanent )
3261
+ unlink (PGSTAT_STAT_PERMANENT_FILENAME );
3262
+
3247
3263
return dbhash ;
3248
3264
}
3249
3265
@@ -3262,9 +3278,9 @@ backend_read_statsfile(void)
3262
3278
3263
3279
/* Autovacuum launcher wants stats about all databases */
3264
3280
if (IsAutoVacuumLauncherProcess ())
3265
- pgStatDBHash = pgstat_read_statsfile (InvalidOid );
3281
+ pgStatDBHash = pgstat_read_statsfile (InvalidOid , false );
3266
3282
else
3267
- pgStatDBHash = pgstat_read_statsfile (MyDatabaseId );
3283
+ pgStatDBHash = pgstat_read_statsfile (MyDatabaseId , false );
3268
3284
}
3269
3285
3270
3286
0 commit comments