127 lines
2.9 KiB
Perl
127 lines
2.9 KiB
Perl
#!/usr/bin/perl
|
|
#
|
|
# Generate lwlocknames.h from lwlocklist.h
|
|
# Copyright (c) 2000-2024, PostgreSQL Global Development Group
|
|
|
|
use strict;
|
|
use warnings FATAL => 'all';
|
|
use Getopt::Long;
|
|
|
|
my $output_path = '.';
|
|
|
|
my $lastlockidx = -1;
|
|
my $continue = "\n";
|
|
|
|
GetOptions('outdir:s' => \$output_path);
|
|
|
|
open my $lwlocklist, '<', $ARGV[0] or die;
|
|
open my $wait_event_names, '<', $ARGV[1] or die;
|
|
|
|
# Include PID in suffix in case parallel make runs this multiple times.
|
|
my $htmp = "$output_path/lwlocknames.h.tmp$$";
|
|
open my $h, '>', $htmp or die "Could not open $htmp: $!";
|
|
|
|
my $autogen =
|
|
"/* autogenerated from src/include/storage/lwlocklist.h, do not edit */\n";
|
|
print $h $autogen;
|
|
print $h "/* there is deliberately not an #ifndef LWLOCKNAMES_H here */\n\n";
|
|
|
|
|
|
#
|
|
# First, record the predefined LWLocks listed in wait_event_names.txt. We'll
|
|
# cross-check those with the ones in lwlocklist.h.
|
|
#
|
|
my @wait_event_lwlocks;
|
|
my $record_lwlocks = 0;
|
|
|
|
while (<$wait_event_names>)
|
|
{
|
|
chomp;
|
|
|
|
# Check for end marker.
|
|
last if /^# END OF PREDEFINED LWLOCKS/;
|
|
|
|
# Skip comments and empty lines.
|
|
next if /^#/;
|
|
next if /^\s*$/;
|
|
|
|
# Start recording LWLocks when we find the WaitEventLWLock section.
|
|
if (/^Section: ClassName - WaitEventLWLock$/)
|
|
{
|
|
$record_lwlocks = 1;
|
|
next;
|
|
}
|
|
|
|
# Go to the next line if we are not yet recording LWLocks.
|
|
next if not $record_lwlocks;
|
|
|
|
# Record the LWLock.
|
|
(my $waiteventname, my $waitevendocsentence) = split(/\t/, $_);
|
|
push(@wait_event_lwlocks, $waiteventname);
|
|
}
|
|
|
|
my $in_comment = 0;
|
|
my $i = 0;
|
|
while (<$lwlocklist>)
|
|
{
|
|
chomp;
|
|
|
|
# Skip single-line C comments and empty lines
|
|
next if m{^\s*/\*.*\*/$};
|
|
next if /^\s*$/;
|
|
|
|
# skip multiline C comments
|
|
if ($in_comment == 1)
|
|
{
|
|
$in_comment = 0 if m{\*/};
|
|
next;
|
|
}
|
|
elsif (m{^\s*/\*})
|
|
{
|
|
$in_comment = 1;
|
|
next;
|
|
}
|
|
|
|
die "unable to parse lwlocklist.h line \"$_\""
|
|
unless /^PG_LWLOCK\((\d+),\s+(\w+)\)$/;
|
|
|
|
(my $lockidx, my $lockname) = ($1, $2);
|
|
|
|
die "lwlocklist.h not in order" if $lockidx < $lastlockidx;
|
|
die "lwlocklist.h has duplicates" if $lockidx == $lastlockidx;
|
|
|
|
die "$lockname defined in lwlocklist.h but missing from "
|
|
. "wait_event_names.txt"
|
|
if $i >= scalar @wait_event_lwlocks;
|
|
die "lists of predefined LWLocks do not match (first mismatch at "
|
|
. "$wait_event_lwlocks[$i] in wait_event_names.txt and $lockname in "
|
|
. "lwlocklist.h)"
|
|
if $wait_event_lwlocks[$i] ne $lockname;
|
|
$i++;
|
|
|
|
while ($lastlockidx < $lockidx - 1)
|
|
{
|
|
++$lastlockidx;
|
|
$continue = ",\n";
|
|
}
|
|
$lastlockidx = $lockidx;
|
|
$continue = ",\n";
|
|
|
|
print $h "#define ${lockname}Lock (&MainLWLockArray[$lockidx].lock)\n";
|
|
}
|
|
|
|
die
|
|
"$wait_event_lwlocks[$i] defined in wait_event_names.txt but missing from "
|
|
. "lwlocklist.h"
|
|
if $i < scalar @wait_event_lwlocks;
|
|
|
|
print $h "\n";
|
|
printf $h "#define NUM_INDIVIDUAL_LWLOCKS %s\n", $lastlockidx + 1;
|
|
|
|
close $h;
|
|
|
|
rename($htmp, "$output_path/lwlocknames.h")
|
|
|| die "rename: $htmp to $output_path/lwlocknames.h: $!";
|
|
|
|
close $lwlocklist;
|