endif # aix
# Update the commonly used headers before building the subdirectories
-$(SUBDIRS:%=%-recursive): $(top_builddir)/src/include/parser/gram.h $(top_builddir)/src/include/catalog/schemapg.h $(top_builddir)/src/include/utils/fmgroids.h $(top_builddir)/src/include/utils/errcodes.h $(top_builddir)/src/include/utils/probes.h
+$(SUBDIRS:%=%-recursive): $(top_builddir)/src/include/parser/gram.h $(top_builddir)/src/include/catalog/schemapg.h $(top_builddir)/src/include/storage/lwlocknames.h $(top_builddir)/src/include/utils/fmgroids.h $(top_builddir)/src/include/utils/errcodes.h $(top_builddir)/src/include/utils/probes.h
# run this unconditionally to avoid needing to know its dependencies here:
submake-schemapg:
parser/gram.h: parser/gram.y
$(MAKE) -C parser gram.h
+storage/lmgr/lwlocknames.h: storage/lmgr/generate-lwlocknames.pl storage/lmgr/lwlocknames.txt
+ $(MAKE) -C storage/lmgr lwlocknames.h
+
utils/fmgroids.h: utils/Gen_fmgrtab.pl catalog/Catalog.pm $(top_srcdir)/src/include/catalog/pg_proc.h
$(MAKE) -C utils fmgroids.h
cd '$(dir $@)' && rm -f $(notdir $@) && \
$(LN_S) "$$prereqdir/$(notdir $<)" .
+$(top_builddir)/src/include/storage/lwlocknames.h: storage/lmgr/lwlocknames.h
+ prereqdir=`cd '$(dir $<)' >/dev/null && pwd` && \
+ cd '$(dir $@)' && rm -f $(notdir $@) && \
+ $(LN_S) "$$prereqdir/$(notdir $<)" .
+
$(top_builddir)/src/include/utils/errcodes.h: utils/errcodes.h
prereqdir=`cd '$(dir $<)' >/dev/null && pwd` && \
cd '$(dir $@)' && rm -f $(notdir $@) && \
$(MAKE) -C bootstrap bootparse.c bootscanner.c
$(MAKE) -C catalog schemapg.h postgres.bki postgres.description postgres.shdescription
$(MAKE) -C replication repl_gram.c repl_scanner.c
+ $(MAKE) -C storage lwlocknames.h
$(MAKE) -C utils fmgrtab.c fmgroids.h errcodes.h
$(MAKE) -C utils/misc guc-file.c
$(MAKE) -C utils/sort qsort_tuple.c
rm -f $(LOCALOBJS) postgres$(X) $(POSTGRES_IMP) \
$(top_builddir)/src/include/parser/gram.h \
$(top_builddir)/src/include/catalog/schemapg.h \
+ $(top_builddir)/src/include/storage/lwlocknames.h \
$(top_builddir)/src/include/utils/fmgroids.h \
$(top_builddir)/src/include/utils/probes.h
ifeq ($(PORTNAME), cygwin)
catalog/postgres.shdescription \
replication/repl_gram.c \
replication/repl_scanner.c \
+ storage/lmgr/lwlocknames.c \
+ storage/lmgr/lwlocknames.h \
utils/fmgroids.h \
utils/fmgrtab.c \
utils/errcodes.h \
--- /dev/null
+/lwlocknames.c
+/lwlocknames.h
$(CC) $(CPPFLAGS) $(CFLAGS) -DS_LOCK_TEST=1 $(srcdir)/s_lock.c \
$(TASPATH) -L $(top_builddir)/src/port -lpgport -o s_lock_test
+# see explanation in ../../parser/Makefile
+lwlocknames.c: lwlocknames.h ;
+
+lwlocknames.h: $(top_srcdir)/src/backend/storage/lmgr/lwlocknames.txt generate-lwlocknames.pl
+ $(PERL) $(srcdir)/generate-lwlocknames.pl $<
+
check: s_lock_test
./s_lock_test
-clean distclean maintainer-clean:
+clean distclean:
rm -f s_lock_test
+
+maintainer-clean: clean
+ rm -f lwlocknames.h lwlocknames.c
--- /dev/null
+#!/usr/bin/perl
+#
+# Generate lwlocknames.h and lwlocknames.c from lwlocknames.txt
+# Copyright (c) 2000-2015, PostgreSQL Global Development Group
+
+use warnings;
+use strict;
+
+my $lastlockidx = -1;
+my $continue = "\n";
+
+open my $lwlocknames, $ARGV[0] or die;
+
+# Include PID in suffix in case parallel make runs this multiple times.
+my $htmp = "lwlocknames.h.tmp$$";
+my $ctmp = "lwlocknames.c.tmp$$";
+open H, '>', $htmp or die "Could not open $htmp: $!";
+open C, '>', $ctmp or die "Could not open $ctmp: $!";
+
+my $autogen =
+ "/* autogenerated from src/backend/storage/lmgr/lwlocknames.txt, do not edit */\n";
+print H $autogen;
+print H "/* there is deliberately not an #ifndef LWLOCKNAMES_H here */\n\n";
+print C $autogen, "\n";
+
+print C "static char *MainLWLockNames[] = {";
+
+while (<$lwlocknames>)
+{
+ chomp;
+
+ # Skip comments
+ next if /^#/;
+ next if /^\s*$/;
+
+ die "unable to parse lwlocknames.txt"
+ unless /^(\w+)\s+(\d+)$/;
+
+ (my $lockname, my $lockidx) = ($1, $2);
+
+ die "lwlocknames.txt not in order" if $lockidx < $lastlockidx;
+ die "lwlocknames.txt has duplicates" if $lockidx == $lastlockidx;
+
+ while ($lastlockidx < $lockidx - 1)
+ {
+ ++$lastlockidx;
+ printf C "%s \"<unassigned:%d>\"", $continue, $lastlockidx;
+ $continue = ",\n";
+ }
+ printf C "%s \"%s\"", $continue, $lockname;
+ $lastlockidx = $lockidx;
+ $continue = ",\n";
+
+ print H "#define $lockname (&MainLWLockArray[$lockidx].lock)\n";
+}
+
+printf C "\n};\n";
+print H "\n";
+printf H "#define NUM_INDIVIDUAL_LWLOCKS %s\n", $lastlockidx + 1;
+
+close H;
+close C;
+
+rename($htmp, 'lwlocknames.h') || die "rename: $htmp: $!";
+rename($ctmp, 'lwlocknames.c') || die "rename: $ctmp: $!";
+
+close $lwlocknames;
#include "utils/hsearch.h"
#endif
+/* Constants for lwlock names */
+#include "lwlocknames.c"
+
/* We use the ShmemLock spinlock to protect LWLockAssign */
extern slock_t *ShmemLock;
if (Trace_lwlocks)
{
uint32 state = pg_atomic_read_u32(&lock->state);
-
- ereport(LOG,
- (errhidestmt(true),
- errhidecontext(true),
- errmsg("%d: %s(%s %d): excl %u shared %u haswaiters %u waiters %u rOK %d",
- MyProcPid,
- where, T_NAME(lock), T_ID(lock),
- !!(state & LW_VAL_EXCLUSIVE),
- state & LW_SHARED_MASK,
- !!(state & LW_FLAG_HAS_WAITERS),
- pg_atomic_read_u32(&lock->nwaiters),
- !!(state & LW_FLAG_RELEASE_OK))));
+ int id = T_ID(lock);
+
+ if (lock->tranche == 0 && id < NUM_INDIVIDUAL_LWLOCKS)
+ ereport(LOG,
+ (errhidestmt(true),
+ errhidecontext(true),
+ errmsg("%d: %s(%s): excl %u shared %u haswaiters %u waiters %u rOK %d",
+ MyProcPid,
+ where, MainLWLockNames[id],
+ !!(state & LW_VAL_EXCLUSIVE),
+ state & LW_SHARED_MASK,
+ !!(state & LW_FLAG_HAS_WAITERS),
+ pg_atomic_read_u32(&lock->nwaiters),
+ !!(state & LW_FLAG_RELEASE_OK))));
+ else
+ ereport(LOG,
+ (errhidestmt(true),
+ errhidecontext(true),
+ errmsg("%d: %s(%s %d): excl %u shared %u haswaiters %u waiters %u rOK %d",
+ MyProcPid,
+ where, T_NAME(lock), id,
+ !!(state & LW_VAL_EXCLUSIVE),
+ state & LW_SHARED_MASK,
+ !!(state & LW_FLAG_HAS_WAITERS),
+ pg_atomic_read_u32(&lock->nwaiters),
+ !!(state & LW_FLAG_RELEASE_OK))));
}
}
/* hide statement & context here, otherwise the log is just too verbose */
if (Trace_lwlocks)
{
- ereport(LOG,
- (errhidestmt(true),
- errhidecontext(true),
- errmsg("%s(%s %d): %s", where,
- T_NAME(lock), T_ID(lock), msg)));
+ int id = T_ID(lock);
+
+ if (lock->tranche == 0 && id < NUM_INDIVIDUAL_LWLOCKS)
+ ereport(LOG,
+ (errhidestmt(true),
+ errhidecontext(true),
+ errmsg("%s(%s): %s", where,
+ MainLWLockNames[id], msg)));
+ else
+ ereport(LOG,
+ (errhidestmt(true),
+ errhidecontext(true),
+ errmsg("%s(%s %d): %s", where,
+ T_NAME(lock), id, msg)));
}
}
--- /dev/null
+# Some commonly-used locks have predefined positions within MainLWLockArray;
+# these are defined here. If you add a lock, add it to the end to avoid
+# renumbering the existing locks; if you remove a lock, consider leaving a gap
+# in the numbering sequence for the benefit of DTrace and other external
+# debugging scripts.
+
+# 0 is available; was formerly BufFreelistLock
+ShmemIndexLock 1
+OidGenLock 2
+XidGenLock 3
+ProcArrayLock 4
+SInvalReadLock 5
+SInvalWriteLock 6
+WALBufMappingLock 7
+WALWriteLock 8
+ControlFileLock 9
+CheckpointLock 10
+CLogControlLock 11
+SubtransControlLock 12
+MultiXactGenLock 13
+MultiXactOffsetControlLock 14
+MultiXactMemberControlLock 15
+RelCacheInitLock 16
+CheckpointerCommLock 17
+TwoPhaseStateLock 18
+TablespaceCreateLock 19
+BtreeVacuumLock 20
+AddinShmemInitLock 21
+AutovacuumLock 22
+AutovacuumScheduleLock 23
+SyncScanLock 24
+RelationMappingLock 25
+AsyncCtlLock 26
+AsyncQueueLock 27
+SerializableXactHashLock 28
+SerializableFinishedListLock 29
+SerializablePredicateLockListLock 30
+OldSerXidLock 31
+SyncRepLock 32
+BackgroundWorkerLock 33
+DynamicSharedMemoryControlLock 34
+AutoFileLock 35
+ReplicationSlotAllocationLock 36
+ReplicationSlotControlLock 37
+CommitTsControlLock 38
+CommitTsLock 39
+ReplicationOriginLock 40
--- /dev/null
+/lwlocknames.h
} LWLockPadded;
extern PGDLLIMPORT LWLockPadded *MainLWLockArray;
-/*
- * Some commonly-used locks have predefined positions within MainLWLockArray;
- * defining macros here makes it much easier to keep track of these. If you
- * add a lock, add it to the end to avoid renumbering the existing locks;
- * if you remove a lock, consider leaving a gap in the numbering sequence for
- * the benefit of DTrace and other external debugging scripts.
- */
-/* 0 is available; was formerly BufFreelistLock */
-#define ShmemIndexLock (&MainLWLockArray[1].lock)
-#define OidGenLock (&MainLWLockArray[2].lock)
-#define XidGenLock (&MainLWLockArray[3].lock)
-#define ProcArrayLock (&MainLWLockArray[4].lock)
-#define SInvalReadLock (&MainLWLockArray[5].lock)
-#define SInvalWriteLock (&MainLWLockArray[6].lock)
-#define WALBufMappingLock (&MainLWLockArray[7].lock)
-#define WALWriteLock (&MainLWLockArray[8].lock)
-#define ControlFileLock (&MainLWLockArray[9].lock)
-#define CheckpointLock (&MainLWLockArray[10].lock)
-#define CLogControlLock (&MainLWLockArray[11].lock)
-#define SubtransControlLock (&MainLWLockArray[12].lock)
-#define MultiXactGenLock (&MainLWLockArray[13].lock)
-#define MultiXactOffsetControlLock (&MainLWLockArray[14].lock)
-#define MultiXactMemberControlLock (&MainLWLockArray[15].lock)
-#define RelCacheInitLock (&MainLWLockArray[16].lock)
-#define CheckpointerCommLock (&MainLWLockArray[17].lock)
-#define TwoPhaseStateLock (&MainLWLockArray[18].lock)
-#define TablespaceCreateLock (&MainLWLockArray[19].lock)
-#define BtreeVacuumLock (&MainLWLockArray[20].lock)
-#define AddinShmemInitLock (&MainLWLockArray[21].lock)
-#define AutovacuumLock (&MainLWLockArray[22].lock)
-#define AutovacuumScheduleLock (&MainLWLockArray[23].lock)
-#define SyncScanLock (&MainLWLockArray[24].lock)
-#define RelationMappingLock (&MainLWLockArray[25].lock)
-#define AsyncCtlLock (&MainLWLockArray[26].lock)
-#define AsyncQueueLock (&MainLWLockArray[27].lock)
-#define SerializableXactHashLock (&MainLWLockArray[28].lock)
-#define SerializableFinishedListLock (&MainLWLockArray[29].lock)
-#define SerializablePredicateLockListLock (&MainLWLockArray[30].lock)
-#define OldSerXidLock (&MainLWLockArray[31].lock)
-#define SyncRepLock (&MainLWLockArray[32].lock)
-#define BackgroundWorkerLock (&MainLWLockArray[33].lock)
-#define DynamicSharedMemoryControlLock (&MainLWLockArray[34].lock)
-#define AutoFileLock (&MainLWLockArray[35].lock)
-#define ReplicationSlotAllocationLock (&MainLWLockArray[36].lock)
-#define ReplicationSlotControlLock (&MainLWLockArray[37].lock)
-#define CommitTsControlLock (&MainLWLockArray[38].lock)
-#define CommitTsLock (&MainLWLockArray[39].lock)
-#define ReplicationOriginLock (&MainLWLockArray[40].lock)
-
-#define NUM_INDIVIDUAL_LWLOCKS 41
+/* Names for fixed lwlocks */
+#include "lwlocknames.h"
/*
* It's a bit odd to declare NUM_BUFFER_PARTITIONS and NUM_LOCK_PARTITIONS
'src/include/utils/fmgroids.h');
}
+ if (IsNewer(
+ 'src/include/storage/lwlocknames.h', 'src/backend/storage/lmgr/lwlocknames.txt'))
+ {
+ print "Generating lwlocknames.c and lwlocknames.h...\n";
+ chdir('src/backend/storage/lmgr');
+ system('perl generate-lwlocknames.pl lwlocknames.txt');
+ chdir('../../../..');
+ }
+ if (IsNewer(
+ 'src/include/storage/lwlocknames.h',
+ 'src/backend/storage/lmgr/lwlocknames.h'))
+ {
+ copyFile('src/backend/storage/lmgr/lwlocknames.h',
+ 'src/include/storage/lwlocknames.h');
+ }
+
if (IsNewer('src/include/utils/probes.h', 'src/backend/utils/probes.d'))
{
print "Generating probes.h...\n";