Skip to content

Commit 2a3039a

Browse files
committed
embed.fnc: Add ability to customize ARGS_ASSERT macros
This enhances embed.fnc entries to contain arbitrary assert() calls, which will be added to the corresponding generated ARGS_ASSERT macros. The next commit will use it.
1 parent 3c592f3 commit 2a3039a

File tree

3 files changed

+45
-2
lines changed

3 files changed

+45
-2
lines changed

embed.fnc

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@
3535
: Supported at least since perl-5.23.8, with or without ppport.h.
3636
:
3737
: Lines in this file are of the form:
38-
: flags|return_type|name|arg1|arg2|...|argN
38+
: flags|return_type|name|arg1|arg2|...|argN ( assert(...) )*
3939
:
4040
: 'flags' is a string of single letters. Most of the flags are meaningful only
4141
: to embed.pl; some only to autodoc.pl, and others only to makedef.pl. The
@@ -46,6 +46,9 @@
4646
: A line may be continued onto the next by ending it with a backslash.
4747
: Leading and trailing whitespace will be ignored in each component.
4848
:
49+
: The optional list of asserts is used to customize the generated
50+
: PERL_ARGS_ASSERT macro. See AUTOMATIC PARAMETER SANITY CHECKING below
51+
:
4952
: Most entries here have a macro created with the entry name. This presents
5053
: name space collision potentials which haven't been well thought out, but are
5154
: now documented here. In practice this has rarely been an issue. At least,
@@ -172,6 +175,14 @@
172175
: may not be of the correct type. As already mentioned, NOCHECK
173176
: suppresses this check.
174177
:
178+
: You can specify your own checking beyond these by adding any number of
179+
: assert() calls to any given entry after its final argument. Whatever you
180+
: specify will be added to the ARGS_ASSERT macro for the entry in the order
181+
: you've specified, and after all the assertions that already have been
182+
: described in this section. When adding yours, weigh that doing it here
183+
: will make it less visible to a maintainer than keeping it in the function
184+
: it applies to
185+
:
175186
: Currently, it is optional to include an empty ARGS_ASSERT macro in your
176187
: functions. But a porting test enforces that a non-empty one is included.
177188
: The call should be at the top of your function so that the sanity checks

regen/HeaderParser.pm

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -746,6 +746,11 @@ sub tidy_embed_fnc_entry {
746746
$line =~ s/\s+\z//; # No trailing white space
747747
($line)= expand($line); # No tabs
748748

749+
# Remove any assertions, and save them. This must be done before the
750+
# split because the assertions can contain '|'
751+
$line =~ s/ \b ( assert \s* \( .* ) \z //x;
752+
my $assertions = $1;
753+
749754
# Split into fields
750755
my ($flags, $ret, $name, @args)= split /\s*\|\s*/, $line;
751756

@@ -795,6 +800,28 @@ sub tidy_embed_fnc_entry {
795800
$head .= "|$arg";
796801
$head .= "\\\n" . (" " x 32) if $ix < $#args;
797802
}
803+
804+
my @assertions;
805+
if ($assertions) {
806+
# Put each assertion into a separate array element
807+
@assertions = split / \s* assert \s* \( /x, $assertions;
808+
shift @assertions; # The split leaves an empty first element
809+
810+
# Trim each assertion, including any trailing semicolon
811+
foreach my $this_assertion (@assertions) {
812+
$this_assertion =~ s/ ^ \s+ //x;
813+
$this_assertion =~ s/ \s+ \z //x;
814+
$this_assertion =~ s/ ; \z //x;
815+
816+
# Restore split delimitter
817+
$this_assertion = "assert($this_assertion";
818+
819+
# Each assertion is on a separate line (for now, anyway)
820+
$head .= "\\\n" . (" " x 32);
821+
$head .= $this_assertion;
822+
}
823+
}
824+
798825
$line= $head . "\n";
799826
800827
# Make all lines in this entry the same length; minimum 72
@@ -816,6 +843,7 @@ sub tidy_embed_fnc_entry {
816843
return_type => $ret,
817844
name => $name,
818845
args => \@args,
846+
assertions => \@assertions,
819847
start_line_num => $line_data->{start_line_num},
820848
);
821849

regen/embed.pl

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -121,7 +121,8 @@ sub generate_proto_h {
121121
$ind .= " " x ($level-1) if $level>1;
122122
my $inner_ind= $ind ? " " : " ";
123123

124-
my ($flags,$retval,$plain_func,$args) = @{$embed}{qw(flags return_type name args)};
124+
my ($flags, $retval, $plain_func, $args, $assertions ) =
125+
@{$embed}{qw(flags return_type name args assertions)};
125126
if ($flags =~ / ( [^ AabCDdEefFGhIiMmNnOoPpRrSsTUuvWXx;] ) /xx) {
126127
die_at_end "flag $1 is not legal (for function $plain_func)";
127128
}
@@ -333,6 +334,9 @@ sub generate_proto_h {
333334
}
334335
$ret .= " comma_pDEPTH" if $has_depth;
335336
$ret .= ")";
337+
338+
push @asserts, $assertions->@* if $assertions;
339+
336340
my @attrs;
337341
if ( $flags =~ /r/ ) {
338342
push @attrs, "__attribute__noreturn__";

0 commit comments

Comments
 (0)