@@ -414,6 +414,34 @@ namespace deduction_substitution_failure {
414
414
int bi = B<char , char >; // expected-note {{during template argument deduction for variable template partial specialization 'B<T, typename Fail<T>::error>' [with T = char]}}
415
415
}
416
416
417
+ namespace deduce_pack_from_argument {
418
+ template <typename ... T>
419
+ void separator (args_tag<T...>, T..., int , T...) {}
420
+ template <typename ... T>
421
+ void separator_dependent (args_tag<T...>, type_identity_t <T>..., int , type_identity_t <T>...) {}
422
+ template <typename ... Y, typename ... T>
423
+ void separator_multiple_parameters (args_tag<Y...>, args_tag<T...>, type_identity_t <T>..., int mid, type_identity_t <T>...) {}
424
+
425
+ void test_separator () {
426
+ separator (args_tag<int , int >{}, 4 , 8 , 42 , 16 , 25 );
427
+ separator (args_tag<>{}, 42 );
428
+ separator_dependent (args_tag<int , int >{}, 4 , 8 , 42 , 16 , 25 );
429
+ separator_dependent (args_tag<>{}, 42 );
430
+ separator_multiple_parameters (args_tag<const int , const int >{}, args_tag<int , int >{}, 8 , 9 , 15 , 16 , 23 );
431
+ }
432
+
433
+ template <typename ... Y, typename ... T> void no_separator (args_tag<T...>, T..., T...) {}
434
+ template <typename ... Y, typename ... T>
435
+ void no_separator_dependent (args_tag<Y...>, args_tag<T...>, type_identity_t <T>..., type_identity_t <T>...) {}
436
+
437
+ void test_no_separator () {
438
+ no_separator (args_tag<int , int >{}, 1 , 2 , 3 , 4 );
439
+ no_separator (args_tag<>{});
440
+ no_separator_dependent (args_tag<const int , const int >{}, args_tag<int , int >{}, 8 , 9 , 15 , 16 );
441
+ no_separator_dependent (args_tag<>{}, args_tag<>{});
442
+ }
443
+ }
444
+
417
445
namespace deduction_after_explicit_pack {
418
446
template <typename ...T, typename U> int *f (T ...t, int &r, U *u) {
419
447
return u;
@@ -442,29 +470,6 @@ namespace deduction_after_explicit_pack {
442
470
i<int , int >(0 , 1 , 2 , 3 , 4 , 5 ); // expected-error {{no match}}
443
471
}
444
472
445
- template <typename ... T>
446
- void bar (args_tag<T...>, type_identity_t <T>..., int mid, type_identity_t <T>...) {}
447
- void call_bar () {
448
- bar (args_tag<int , int >{}, 4 , 8 , 1001 , 16 , 23 );
449
- }
450
-
451
- template <typename ... Y, typename ... T>
452
- void foo (args_tag<Y...>, args_tag<T...>, type_identity_t <T>..., int mid, type_identity_t <T>...) {}
453
- void call_foo () {
454
- foo (args_tag<const int ,const int , const int >{}, args_tag<int , int , int >{}, 4 , 8 , 9 , 15 , 16 , 23 , 1 );
455
- }
456
-
457
- template <typename ... Y, typename ... T>
458
- void foo2 (args_tag<Y...>, args_tag<T...>, type_identity_t <T>..., type_identity_t <T>...) {}
459
- void call_foo2 () {
460
- foo2 (args_tag<const int ,const int , const int >{}, args_tag<int , int , int >{}, 4 , 8 , 9 , 15 , 16 , 23 );
461
- }
462
-
463
- template <typename ... Y, typename ... T> void baz (args_tag<T...>, T..., T...) {}
464
- void call_baz () {
465
- baz (args_tag<int , int >{}, 1 , 2 , 3 , 4 );
466
- }
467
-
468
473
// GCC alarmingly accepts this by deducing T={int} by matching the second
469
474
// parameter against the first argument, then passing the first argument
470
475
// through the first parameter.
0 commit comments