summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorgregor herrmann <gregoa@debian.org>2023-09-20 21:39:16 +0200
committergregor herrmann <gregoa@debian.org>2023-09-20 21:39:16 +0200
commita32a9cc1169b6d2966ba0f3ee110c00fd4d05aac (patch)
tree6ba411c57557fc6881d0e658dbf0e39c0092c31e
parent3310bddcb190577fa8960eda1cf8b8294483adfd (diff)
parentd42a873f6b8b26a40c1b009de577bc31feb15394 (diff)
Update upstream source from tag 'upstream/0.66'
Update to upstream version '0.66' with Debian dir 9379998c26554363445924e9ee5922f11c4c1c51
-rw-r--r--.editorconfig4
-rw-r--r--Changes10
-rw-r--r--MANIFEST2
-rw-r--r--META.json12
-rw-r--r--META.yml12
-rw-r--r--hax/perl-additions.c.inc9
-rw-r--r--hax/perl-backcompat.c.inc36
-rw-r--r--lib/Future/AsyncAwait.pm35
-rw-r--r--lib/Future/AsyncAwait.xs1
-rw-r--r--lib/Future/AsyncAwait/Awaitable.pm2
-rw-r--r--lib/Future/AsyncAwait/ExtensionBuilder.pm4
-rw-r--r--lib/Future/AsyncAwait/ExtensionBuilder_data.pm.PL2
-rw-r--r--lib/Test/Future/AsyncAwait/Awaitable.pm2
-rw-r--r--t/01async-immediate.t9
-rw-r--r--t/70await+feature-class.t70
-rw-r--r--t/80async-method.t8
-rw-r--r--t/81async-method+dynamically.t6
17 files changed, 176 insertions, 48 deletions
diff --git a/.editorconfig b/.editorconfig
new file mode 100644
index 0000000..24b6e3b
--- /dev/null
+++ b/.editorconfig
@@ -0,0 +1,4 @@
+root = true
+
+[*.{pm,pl,t}]
+indent_size = 3
diff --git a/Changes b/Changes
index 0add03d..8e09209 100644
--- a/Changes
+++ b/Changes
@@ -1,5 +1,15 @@
Revision history for Future-AsyncAwait
+0.66 2023-09-08
+ [CHANGES]
+ * Add a unit test to check that `async method` works on core perl
+ class syntax
+ * Remember to implement `sub unimport` so that `no Future::AsyncAwait`
+ works
+
+ [BUGFIXES]
+ * Provide a permit_hintkey to keep XPS happy
+
0.65 2023-03-17
[CHANGES]
* More specific unit-testing of the croak location when testing
diff --git a/MANIFEST b/MANIFEST
index ccf258a..7451b7c 100644
--- a/MANIFEST
+++ b/MANIFEST
@@ -1,3 +1,4 @@
+.editorconfig
Build.PL
Changes
hax/cv_copy_flags.c.inc
@@ -56,6 +57,7 @@ t/45sub-signatures.t
t/50future-subclass.t
t/51awaitable-role.t
t/52awaitable-future.t
+t/70await+feature-class.t
t/70await+feature-try.t
t/80async-method.t
t/80async-multi-sub.t
diff --git a/META.json b/META.json
index c5e31f2..2c012e2 100644
--- a/META.json
+++ b/META.json
@@ -4,7 +4,7 @@
"Paul Evans <leonerd@leonerd.org.uk>"
],
"dynamic_config" : 1,
- "generated_by" : "Module::Build version 0.4231",
+ "generated_by" : "Module::Build version 0.4234",
"license" : [
"perl_5"
],
@@ -44,19 +44,19 @@
"provides" : {
"Future::AsyncAwait" : {
"file" : "lib/Future/AsyncAwait.pm",
- "version" : "0.65"
+ "version" : "0.66"
},
"Future::AsyncAwait::Awaitable" : {
"file" : "lib/Future/AsyncAwait/Awaitable.pm",
- "version" : "0.65"
+ "version" : "0.66"
},
"Future::AsyncAwait::ExtensionBuilder" : {
"file" : "lib/Future/AsyncAwait/ExtensionBuilder.pm",
- "version" : "0.65"
+ "version" : "0.66"
},
"Test::Future::AsyncAwait::Awaitable" : {
"file" : "lib/Test/Future/AsyncAwait/Awaitable.pm",
- "version" : "0.65"
+ "version" : "0.66"
}
},
"release_status" : "stable",
@@ -66,6 +66,6 @@
],
"x_IRC" : "irc://irc.perl.org/#io-async"
},
- "version" : "0.65",
+ "version" : "0.66",
"x_serialization_backend" : "JSON::PP version 4.07"
}
diff --git a/META.yml b/META.yml
index 2500113..c844700 100644
--- a/META.yml
+++ b/META.yml
@@ -11,7 +11,7 @@ configure_requires:
XS::Parse::Keyword::Builder: '0.13'
XS::Parse::Sublike::Builder: '0.14'
dynamic_config: 1
-generated_by: 'Module::Build version 0.4231, CPAN::Meta::Converter version 2.150010'
+generated_by: 'Module::Build version 0.4234, CPAN::Meta::Converter version 2.150010'
license: perl
meta-spec:
url: http://module-build.sourceforge.net/META-spec-v1.4.html
@@ -20,16 +20,16 @@ name: Future-AsyncAwait
provides:
Future::AsyncAwait:
file: lib/Future/AsyncAwait.pm
- version: '0.65'
+ version: '0.66'
Future::AsyncAwait::Awaitable:
file: lib/Future/AsyncAwait/Awaitable.pm
- version: '0.65'
+ version: '0.66'
Future::AsyncAwait::ExtensionBuilder:
file: lib/Future/AsyncAwait/ExtensionBuilder.pm
- version: '0.65'
+ version: '0.66'
Test::Future::AsyncAwait::Awaitable:
file: lib/Test/Future/AsyncAwait/Awaitable.pm
- version: '0.65'
+ version: '0.66'
requires:
Future: '0.50'
XS::Parse::Keyword: '0.13'
@@ -38,5 +38,5 @@ requires:
resources:
IRC: irc://irc.perl.org/#io-async
license: http://dev.perl.org/licenses/
-version: '0.65'
+version: '0.66'
x_serialization_backend: 'CPAN::Meta::YAML version 0.018'
diff --git a/hax/perl-additions.c.inc b/hax/perl-additions.c.inc
index 939b64b..82cc0f2 100644
--- a/hax/perl-additions.c.inc
+++ b/hax/perl-additions.c.inc
@@ -173,12 +173,13 @@ static void S_ensure_module_version(pTHX_ SV *module, SV *version)
}
#if HAVE_PERL_VERSION(5, 16, 0)
+ /* TODO: perl 5.14 lacks HvNAMEUTF8, gv_fetchmeth_pvn() */
# define fetch_superclass_method_pv(stash, pv, len, level) S_fetch_superclass_method_pv(aTHX_ stash, pv, len, level)
static CV *S_fetch_superclass_method_pv(pTHX_ HV *stash, const char *pv, STRLEN len, U32 level)
{
-#if HAVE_PERL_VERSION(5, 18, 0)
+# if HAVE_PERL_VERSION(5, 18, 0)
GV *gv = gv_fetchmeth_pvn(stash, pv, len, level, GV_SUPER);
-#else
+# else
SV *superclassname = newSVpvf("%*s::SUPER", HvNAMELEN_get(stash), HvNAME_get(stash));
if(HvNAMEUTF8(stash))
SvUTF8_on(superclassname);
@@ -186,13 +187,13 @@ static CV *S_fetch_superclass_method_pv(pTHX_ HV *stash, const char *pv, STRLEN
HV *superstash = gv_stashsv(superclassname, GV_ADD);
GV *gv = gv_fetchmeth_pvn(superstash, pv, len, level, 0);
-#endif
+# endif
if(!gv)
return NULL;
return GvCV(gv);
}
-#endif
+#endif /* HAVE_PERL_VERSION(5, 16, 0) */
#define get_class_isa(stash) S_get_class_isa(aTHX_ stash)
static AV *S_get_class_isa(pTHX_ HV *stash)
diff --git a/hax/perl-backcompat.c.inc b/hax/perl-backcompat.c.inc
index 09e521b..5380102 100644
--- a/hax/perl-backcompat.c.inc
+++ b/hax/perl-backcompat.c.inc
@@ -34,6 +34,16 @@ typedef SV PADNAME;
#if !HAVE_PERL_VERSION(5, 22, 0)
# define CvPADLIST_set(cv, padlist) (CvPADLIST(cv) = padlist)
+# define newPADNAMEpvn(p,n) S_newPADNAMEpvn(aTHX_ p,n)
+static PADNAME *S_newPADNAMEpvn(pTHX_ const char *pv, STRLEN n)
+{
+ PADNAME *pn = newSVpvn(pv, n);
+ /* PADNAMEs need to be at least SVt_PVNV in order to store the COP_SEQ_*
+ * fields */
+ sv_upgrade(pn, SVt_PVNV);
+ return pn;
+}
+# define PadnameREFCNT_dec(pn) SvREFCNT_dec(pn)
#endif
#ifndef av_count
@@ -52,6 +62,10 @@ typedef SV PADNAME;
# define block_start(a) Perl_block_start(aTHX_ a)
#endif
+#ifndef cophh_exists_pvs
+# define cophh_exists_pvs(a,b,c) cBOOL(cophh_fetch_pvs(a,b,c))
+#endif
+
#ifndef cv_clone
# define cv_clone(a) Perl_cv_clone(aTHX_ a)
#endif
@@ -78,6 +92,10 @@ typedef SV PADNAME;
# define OpSIBLING(op) ((op)->op_sibling)
#endif
+#ifndef OpHAS_SIBLING
+# define OpHAS_SIBLING(op) (cBOOL(OpSIBLING(op)))
+#endif
+
#ifndef OpMORESIB_set
# define OpMORESIB_set(op,sib) ((op)->op_sibling = (sib))
#endif
@@ -180,16 +198,18 @@ static bool MY_sv_derived_from_hv(pTHX_ SV *sv, HV *hv)
}
#endif
-#ifdef PERL_USE_GCC_BRACE_GROUPS
-# define xV_FROM_REF(XV, ref) \
+#ifndef xV_FROM_REF
+# ifdef PERL_USE_GCC_BRACE_GROUPS
+# define xV_FROM_REF(XV, ref) \
({ SV *_ref = ref; assert(SvROK(_ref)); assert(SvTYPE(SvRV(_ref)) == SVt_PV ## XV); (XV *)(SvRV(_ref)); })
-#else
-# define xV_FROM_REF(XV, ref) ((XV *)SvRV(ref))
-#endif
+# else
+# define xV_FROM_REF(XV, ref) ((XV *)SvRV(ref))
+# endif
-#define AV_FROM_REF(ref) xV_FROM_REF(AV, ref)
-#define CV_FROM_REF(ref) xV_FROM_REF(CV, ref)
-#define HV_FROM_REF(ref) xV_FROM_REF(HV, ref)
+# define AV_FROM_REF(ref) xV_FROM_REF(AV, ref)
+# define CV_FROM_REF(ref) xV_FROM_REF(CV, ref)
+# define HV_FROM_REF(ref) xV_FROM_REF(HV, ref)
+#endif
#ifndef newPADxVOP
# define newPADxVOP(type, flags, padix) S_newPADxVOP(aTHX_ type, flags, padix)
diff --git a/lib/Future/AsyncAwait.pm b/lib/Future/AsyncAwait.pm
index 0d9fe9c..2cc5a7b 100644
--- a/lib/Future/AsyncAwait.pm
+++ b/lib/Future/AsyncAwait.pm
@@ -3,7 +3,7 @@
#
# (C) Paul Evans, 2016-2021 -- leonerd@leonerd.org.uk
-package Future::AsyncAwait 0.65;
+package Future::AsyncAwait 0.66;
use v5.14;
use warnings;
@@ -495,31 +495,42 @@ modifier can be applied to C<async sub>.
sub import
{
- my $class = shift;
+ my $pkg = shift;
my $caller = caller;
- $class->import_into( $caller, @_ );
+ $pkg->import_into( $caller, @_ );
}
+sub unimport
+{
+ my $pkg = shift;
+ my $caller = caller;
+
+ $pkg->unimport_into( $caller, @_ );
+}
+
+sub import_into { shift->apply( sub { $^H{ $_[0] }++ }, @_ ) }
+sub unimport_into { shift->apply( sub { delete $^H{ $_[0] } }, @_ ) }
+
my @EXPERIMENTAL = qw( cancel );
-sub import_into
+sub apply
{
- my $class = shift;
- my $caller = shift;
+ my $pkg = shift;
+ my ( $cb, $caller, @syms ) = @_;
- $^H{"Future::AsyncAwait/async"}++; # Just always turn this on
+ $cb->( "Future::AsyncAwait/async" ); # Just always turn this on
- SYM: while( @_ ) {
- my $sym = shift;
+ SYM: while( @syms ) {
+ my $sym = shift @syms;
- $^H{"Future::AsyncAwait/future"} = shift, next if $sym eq "future_class";
+ $^H{"Future::AsyncAwait/future"} = shift @syms, next if $sym eq "future_class";
foreach ( @EXPERIMENTAL ) {
- $^H{"Future::AsyncAwait/experimental($_)"}++, next SYM if $sym eq ":experimental($_)";
+ $cb->( "Future::AsyncAwait/experimental($_)" ), next SYM if $sym eq ":experimental($_)";
}
if( $sym eq ":experimental" ) {
- $^H{"Future::AsyncAwait/experimental($_)"}++ for @EXPERIMENTAL;
+ $cb->( "Future::AsyncAwait/experimental($_)" ) for @EXPERIMENTAL;
next SYM;
}
diff --git a/lib/Future/AsyncAwait.xs b/lib/Future/AsyncAwait.xs
index 7eb8c7a..80f5b53 100644
--- a/lib/Future/AsyncAwait.xs
+++ b/lib/Future/AsyncAwait.xs
@@ -2357,6 +2357,7 @@ static void parse_post_newcv(pTHX_ struct XSParseSublikeContext *ctx, void *hook
}
static struct XSParseSublikeHooks hooks_async = {
+ .permit_hintkey = "Future::AsyncAwait/async",
.flags = XS_PARSE_SUBLIKE_FLAG_PREFIX,
.post_blockstart = parse_post_blockstart,
diff --git a/lib/Future/AsyncAwait/Awaitable.pm b/lib/Future/AsyncAwait/Awaitable.pm
index 89ca9e3..a7ffac2 100644
--- a/lib/Future/AsyncAwait/Awaitable.pm
+++ b/lib/Future/AsyncAwait/Awaitable.pm
@@ -3,7 +3,7 @@
#
# (C) Paul Evans, 2019-2022 -- leonerd@leonerd.org.uk
-package Future::AsyncAwait::Awaitable 0.65;
+package Future::AsyncAwait::Awaitable 0.66;
use v5.14;
use warnings;
diff --git a/lib/Future/AsyncAwait/ExtensionBuilder.pm b/lib/Future/AsyncAwait/ExtensionBuilder.pm
index 389218a..5426c28 100644
--- a/lib/Future/AsyncAwait/ExtensionBuilder.pm
+++ b/lib/Future/AsyncAwait/ExtensionBuilder.pm
@@ -3,14 +3,14 @@
#
# (C) Paul Evans, 2022 -- leonerd@leonerd.org.uk
-package Future::AsyncAwait::ExtensionBuilder 0.65;
+package Future::AsyncAwait::ExtensionBuilder 0.66;
use v5.14;
use warnings;
=head1 NAME
-C<Future::AsyncAwait::ExtensonBuilder> - build-time support for extensions to C<Future::AsyncAwait>
+C<Future::AsyncAwait::ExtensionBuilder> - build-time support for extensions to C<Future::AsyncAwait>
=head1 SYNOPSIS
diff --git a/lib/Future/AsyncAwait/ExtensionBuilder_data.pm.PL b/lib/Future/AsyncAwait/ExtensionBuilder_data.pm.PL
index f2f5df3..752b071 100644
--- a/lib/Future/AsyncAwait/ExtensionBuilder_data.pm.PL
+++ b/lib/Future/AsyncAwait/ExtensionBuilder_data.pm.PL
@@ -19,7 +19,7 @@ $outh->print( scalar do {
<$in_h> } );
__DATA__
-package Future::AsyncAwait::ExtensionBuilder_data 0.65;
+package Future::AsyncAwait::ExtensionBuilder_data 0.66;
use v5.14;
use warnings;
diff --git a/lib/Test/Future/AsyncAwait/Awaitable.pm b/lib/Test/Future/AsyncAwait/Awaitable.pm
index 8b4d19c..80f3801 100644
--- a/lib/Test/Future/AsyncAwait/Awaitable.pm
+++ b/lib/Test/Future/AsyncAwait/Awaitable.pm
@@ -3,7 +3,7 @@
#
# (C) Paul Evans, 2020-2023 -- leonerd@leonerd.org.uk
-package Test::Future::AsyncAwait::Awaitable 0.65;
+package Test::Future::AsyncAwait::Awaitable 0.66;
use v5.14;
use warnings;
diff --git a/t/01async-immediate.t b/t/01async-immediate.t
index 726cb05..bca958a 100644
--- a/t/01async-immediate.t
+++ b/t/01async-immediate.t
@@ -81,4 +81,13 @@ use Future::AsyncAwait;
isa_ok( shift @ret, [ "Future" ], 'Single result was a Future' );
}
+# unimport
+{
+ no Future::AsyncAwait;
+
+ sub async { return "normal function" }
+
+ is( async, "normal function", 'async() parses as a normal function call' );
+}
+
done_testing;
diff --git a/t/70await+feature-class.t b/t/70await+feature-class.t
new file mode 100644
index 0000000..782d886
--- /dev/null
+++ b/t/70await+feature-class.t
@@ -0,0 +1,70 @@
+#!/usr/bin/perl
+
+use v5.14;
+use warnings;
+
+use Test2::V0 0.000148; # is_oneref
+
+BEGIN {
+ plan skip_all => "Future >= 0.49 is not available"
+ unless eval { require Future;
+ Future->VERSION( '0.49' ) };
+ plan skip_all => "Future::AsyncAwait >= 0.45 is not available"
+ unless eval { require Future::AsyncAwait;
+ Future::AsyncAwait->VERSION( '0.45' ) };
+ # version 5.37.10 added the ability to start_subparse() with CVf_IsMETHOD,
+ # which we need
+ plan skip_all => "feature 'class' is not available"
+ unless $^V ge v5.37.10;
+ plan skip_all => "XS::Parse::Sublike >= 0.17 is not in use"
+ unless $XS::Parse::Sublike::VERSION >= 0.17;
+
+ # If Future::XS is installed, then check it's at least 0.08; earlier
+ # versions will crash
+ if( eval { require Future::XS } ) {
+ plan skip_all => "Future::XS is installed but it is older than 0.08"
+ unless eval { Future::AsyncAwait->VERSION( '0.08' ); };
+ }
+
+ diag( "Future::AsyncAwait $Future::AsyncAwait::VERSION, " .
+ "core perl version $^V" );
+}
+
+use Future::AsyncAwait;
+
+use feature 'class';
+no warnings 'experimental::class';
+
+# async method
+{
+ class Thunker {
+ field $_times_thunked = 0;
+
+ method count { $_times_thunked }
+
+ async method thunk {
+ my ( $f ) = @_;
+ await $f;
+ $_times_thunked++;
+ return "result";
+ }
+ }
+
+ my $thunker = Thunker->new;
+ is_oneref( $thunker, 'after ->new' );
+
+ my $f1 = Future->new;
+ my $fret = $thunker->thunk( $f1 );
+ is_refcount( $thunker, 2, 'during async sub' );
+
+ is( $thunker->count, 0, 'count is 0 before $f1->done' );
+
+ $f1->done;
+
+ is_oneref( $thunker, 'after ->done' );
+
+ is( $thunker->count, 1, 'count is 1 after $f1->done' );
+ is( $fret->get, "result", '$fret for await in async method' );
+}
+
+done_testing;
diff --git a/t/80async-method.t b/t/80async-method.t
index 152fd22..f5b8c5a 100644
--- a/t/80async-method.t
+++ b/t/80async-method.t
@@ -3,7 +3,7 @@
use v5.14;
use warnings;
-use Test2::V0 0.000148; # is_oneref
+use Test2::V0 0.000148; # is_refcount
BEGIN {
plan skip_all => "Future >= 0.49 is not available"
@@ -12,9 +12,9 @@ BEGIN {
plan skip_all => "Future::AsyncAwait >= 0.45 is not available"
unless eval { require Future::AsyncAwait;
Future::AsyncAwait->VERSION( '0.45' ) };
- plan skip_all => "Object::Pad >= 0.73 is not available"
+ plan skip_all => "Object::Pad >= 0.800 is not available"
unless eval { require Object::Pad;
- Object::Pad->VERSION( '0.73' ) };
+ Object::Pad->VERSION( '0.800' ) };
# If Future::XS is installed, then check it's at least 0.08; earlier
# versions will crash
@@ -24,7 +24,7 @@ BEGIN {
}
Future::AsyncAwait->import;
- Object::Pad->import( ':experimental(init_expr)' );
+ Object::Pad->import;
diag( "Future::AsyncAwait $Future::AsyncAwait::VERSION, " .
"Object::Pad $Object::Pad::VERSION" );
diff --git a/t/81async-method+dynamically.t b/t/81async-method+dynamically.t
index 9ac3a59..2279176 100644
--- a/t/81async-method+dynamically.t
+++ b/t/81async-method+dynamically.t
@@ -11,15 +11,15 @@ BEGIN {
plan skip_all => "Future::AsyncAwait >= 0.40 is not available"
unless eval { require Future::AsyncAwait;
Future::AsyncAwait->VERSION( '0.40' ) };
- plan skip_all => "Object::Pad >= 0.73 is not available"
+ plan skip_all => "Object::Pad >= 0.800 is not available"
unless eval { require Object::Pad;
- Object::Pad->VERSION( '0.73' ) };
+ Object::Pad->VERSION( '0.800' ) };
plan skip_all => "Syntax::Keyword::Dynamically >= 0.04 is not available"
unless eval { require Syntax::Keyword::Dynamically;
Syntax::Keyword::Dynamically->VERSION( '0.04' ) };
Future::AsyncAwait->import;
- Object::Pad->import( ':experimental(init_expr)' );
+ Object::Pad->import;
Syntax::Keyword::Dynamically->import;
diag( "Future::AsyncAwait $Future::AsyncAwait::VERSION, " .