Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Diagnostic Output for AFMV (#20) #41

Open
wants to merge 1,619 commits into
base: 2024-W-afmv-diagnostic-output
Choose a base branch
from

Conversation

Anatolii-developer
Copy link

Description:

Created test-dump-pass.cc to implement the test dump pass.
Updated Makefile.in to include the new test dump pass.
Updated passes.def to register the new test dump pass.
Thanks for taking the time to contribute to GCC! Please be advised that if you are
viewing this on github.com, that the mirror there is unofficial and unmonitored.
The GCC community does not use github.com for their contributions. Instead, we use
a mailing list ([email protected]) for code submissions, code reviews, and
bug reports. Please send patches there instead.

Thanks for taking the time to contribute to GCC! Please be advised that if you are
viewing this on github.com, that the mirror there is unofficial and unmonitored.
The GCC community does not use github.com for their contributions. Instead, we use
a mailing list ([email protected]) for code submissions, code reviews, and
bug reports. Please send patches there instead.

AdaDoom3 and others added 30 commits June 14, 2024 09:34
This patch modifies the experimental 'Super attribute to allow an access-valued
prefix to be equivalent to Prefix.all'Super.

gcc/ada/

	* sem_attr.adb:
	(Analyze_Attribute): Add check for dereference.
The first cleanup is to expose a consistent interface from Sem_Ch13 for the
analysis of aspects at various points of the program.  The second cleanup is
to fix the awkward implementation of the analysis of the specification for
the aspects Stable_Properties, Designated_Storage_Model, Storage_Model_Type
and Aggregate, which are always delayed, and the incorrect placement of that
of the aspect Local_Restrictions, which is never delayed.

gcc/ada/

	* freeze.adb (Freeze_All): Call Check_Aspects_At_End_Of_Declarations
	to perform the visibility check for aspects.
	* sem_ch13.ads (Check_Aspects_At_End_Of_Declarations): Declare.
	(Check_Aspect_At_Freeze_Point): Move to...
	(Check_Aspect_At_End_Of_Declarations): Move to...
	* sem_ch13.adb 	(Check_Aspect_At_Freeze_Point): ...here.
	(Check_Aspect_At_End_Of_Declarations): ...here.
	(Analyze_Aspect_Specifications): Remove peculiar processing for
	Stable_Properties, Designated_Storage_Model, Storage_Model_Type
	and Aggregate.  Move that of Local_Restrictions around.  Reset
	Aitem at the beginning of the loop for each aspect.
	(Check_Aspects_At_End_Of_Declarations): New procedure.
When a multidimensional array is initialized with an array
aggregate, and inner dimensions of the array are initialized
with array subaggregates using sliding, the code generated
by the compiler does not initialize the inner dimensions
of the array.

gcc/ada/

	* exp_aggr.adb (Must_Slide): Add missing support for
	multidimensional arrays.
The main one is to give the error for Aggregate applied to array types from
Analyze_Aspects_At_Freeze_Point instead of Check_Aspect_At_Freeze_Point, as
for the other aspects.  The message is also changed to be more direct.

gcc/ada/

	* aspects.ads (Operational_Aspect): Alphabetize.
	* sem_ch13.ads (Analyze_Aspects_At_Freeze_Point): Fix description.
	* sem_ch13.adb (Analyze_Aspects_At_Freeze_Point) <Aggregate>: Give
	the error for array types here instead of...
	(Analyze_Aspect_Specifications) <Aggregate>: Adjust comment.
	(Check_Aspect_At_Freeze_Point) <Aggregate>: ...here.
This patch fixes an issue in the compiler whereby calculating a static
accessibility level on a private type with an access discriminant resulted
in a compile time crash when No_Dynamic_Accessibility_Checks is enabled.

gcc/ada/

	* accessibility.adb:
	(Accessibility_Level): Replace call Get_Full_View with call to
	Full_View since Get_Full_View only works with incomplete types.
This patch implements mutably tagged types via the new Size'Class aspect.

gcc/ada/

	* doc/gnat_rm/gnat_language_extensions.rst: Add documentation for
	mutably tagged type feature.
	* aspects.ads: Add registration for 'Size'Class.
	* einfo.ads: Add documentation for new components
	Class_Wide_Equivalent_Type and Is_Mutably_Tagged_Type.
	* exp_aggr.adb (Gen_Assign): Assume associated mutably tagged type
	when class-wide equivalent type is encountered.
	(Contains_Mutably_Tagged_Type): New subprogram.
	(Convert_To_Positional): Assume associated mutably tagged type
	when class-wide equivalent type is encountered.
	(Is_Static_Element): Assume associated mutably tagged type when
	class-wide equivalent type is encountered.
	(Expand_Array_Aggregate): Assume associated mutably tagged type
	when class-wide equivalent type is encountered.
	(Expand_Record_Aggregate): Force mutably tagged records to be
	expanded into assignments.
	* exp_ch3.adb (Build_Array_Init_Proc): Assume associated mutably
	tagged type when class-wide equivalent type is encountered.
	(Simple_Initialization_OK): Disallow simple initialization for
	class-wide equivalent types.
	(Build_Init_Statements): Assume associated mutably tagged type
	when class-wide equivalent type is encountered.
	(Expand_Freeze_Array_Type): Ignore building of record init procs
	for mutably tagged types.
	(Expand_N_Full_Type_Declaration): Replace mutably tagged type
	declarations with their associated class-wide equivalent types.
	(Default_Initialize_Object): Add special handling for mutably
	tagged types.
	* exp_ch4.adb (Expand_N_Allocator): Add initialization for mutably
	tagged types.
	(Expand_Record_Equality): Generate mutably tagged unchecked
	conversions.
	* exp_ch5.adb (Expand_N_Assignment_Statement): Generate a special
	assignment case for class-wide equivalent types which does tag
	assignments and ignores certain checks.
	* exp_ch6.adb (Expand_Call_Helper): Propagate constrained extra
	formal actuals for mutably tagged types.
	* exp_ch7.adb (Make_Init_Call): Handle mutably tagged type
	initialization.
	* exp_util.adb (Make_CW_Equivalent_Type): Modify to handle mutably
	tagged objects which contain no initialization expression.
	(Make_Subtype_From_Expr): Modify call to Make_CW_Equivalent_Type.
	* exp_util.ads (Make_CW_Equivalent_Type): Move declaration from
	body to spec.
	* freeze.adb (Size_Known): No longer return false automatically
	when a class-wide type is encountered.
	(Freeze_Entity): Ignore error messages about size not being known
	for mutably tagged types.
	* gen_il-fields.ads: Register new fields
	Class_Wide_Equivalent_Type and Is_Mutably_Tagged_Type.
	* gen_il-gen-gen_entities.adb: Register new fields
	Class_Wide_Equivalent_Type and Is_Mutably_Tagged_Type for type
	entities.
	* mutably_tagged.adb, mutably_tagged.ads
	(Corresponding_Mutably_Tagged_Type): New subprogram.
	(Depends_On_Mutably_Tagged_Ext_Comp): New subprogram.
	(Get_Corresponding_Mutably_Tagged_Type_If_Present): New
	subprogram.
	(Get_Corresponding_Tagged_Type_If_Present): New subprogram.
	(Is_Mutably_Tagged_Conversion): New subprogram.
	(Is_Mutably_Tagged_CW_Equivalent_Type): New subprogram.
	(Make_Mutably_Tagged_Conversion): New subprogram.
	(Make_CW_Size_Compile_Check): New subprogram.
	(Make_Mutably_Tagged_CW_Check): New subprogram.
	* sem_aggr.adb (Resolve_Array_Aggregate): Skip tag checks for
	class-wide equivalent types.
	(Resolve_Aggr_Expr): Assume associated mutably tagged type when
	class-wide equivalent type is encountered.
	* sem_attr.adb (Analyze_Attribute): Allow 'Tag on mutably tagged
	types.
	(Resolve_Attribute): Detect errors for dependence of mutably
	tagged extension type component.
	* sem_ch12.adb (Instantiate_Object): Detect errors for dependence
	of mutably tagged extension type component.
	* sem_ch13.adb (Analyze_One_Aspect): Propagate 'Size'Class to
	class-wide type.
	(Analyze_Attribute_Definition_Clause): Add handling of 'Size'Class
	by generating class-wide equivalent types and checking for illegal
	uses.
	* sem_ch2.adb (Analyze_Identifier): Generate unchecked conversion
	for class-wide equivalent types.
	* sem_ch3.adb (Analyze_Component_Declaration): Avoid unconstrained
	errors on mutably tagged types.
	(Analyze_Object_Declaration): Rewrite declarations of mutably
	tagged types to use class-wide equivalent types.
	(Array_Type_Declaration): Modify arrays of mutably tagged types to
	use their corresponding class-wide equivalent types.
	(Derived_Type_Declaration): Add various checks for mutably tagged
	derived types.
	* sem_ch4.adb (Analyze_Allocator): Replace reference to mutably
	tagged type with cooresponding tagged type.
	(Process_Indexed_Component): Generate unchecked conversion for
	class-wide equivalent type.
	(Analyze_One_Call): Generate unchecked conversion for class-wide
	equivalent types.
	(Analyze_Selected_Component): Assume reference to class-wide
	equivalent type is associated mutably tagged type.
	(Analyze_Type_Conversion): Generate unchecked conversion for
	class-wide equivalent type.
	* sem_ch5.adb (Analyze_Assignment): Assume associated mutably
	tagged type when class-wide equivalent type is encountered.
	(Analyze_Iterator_Specification): Detect errors for dependence of
	mutably tagged extension type component.
	* sem_ch6.adb (Create_Extra_Formals): Add code to generate extra
	formal for mutably tagged types to signal if they are constrained.
	* sem_ch8.adb (Analyze_Object_Renaming): Detect error on renaming
	of mutably tagged extension type component.
	(Analyze_Renaming_Primitive_Operation): Detect error on renaming
	of mutably tagged extension type component.
	* sem_res.adb (Resolve_Actuals): Allow class-wide arguments on
	class-wide equivalent types.
	(Valid_Conversion): Assume associated mutably tagged type when
	class-wide equivalent type is encountered.
	* sem_util.adb (Is_Fully_Initialized_Type): Flag mutably tagged
	types as fully initialized.
	(Needs_Simple_Initalization): Flag class-wide equivalent types as
	needing initialization.
	* gnat_rm.texi: Regenerate.
	* gcc-interface/Make-lang.in: Add entry for mutably_tagged.o.
gcc/ada/

	* snames.ads-tmpl (Name_Present): Move to Repinfo section.
These error codes were defined on older versions of VxWorks (5, 6, 7
SR0540) and now they are either not defined or they fallback to
ENOENT. To handle these cases without using complex tests against
vxworks versions, leverage on __has_include and provide a fallback to
ENOENT if these error codes are not defined.

gcc/ada/

	* sysdep.c (S_dosFsLib_FILE_NOT_FOUND, S_nfsLib_NFSERR_NOENT):
	New macros, falback to ENOENT when not already defined.
	(__gnat_is_file_not_found_error): Use these new macros to remove
	tests against VxWorks flavors.
…tion

The Etype for an N_Selected_Component node usually should not match the Etype
of the referenced component if the component is subject to a
discriminant-dependent constraint. Instead Build_Actual_Subtype_Of_Component
should be called. Fix a case where this rule was not being followed (because
B_A_S_O_C is not called during preanalysis of a component selection), resulting
in a tree that confused CodePeer because the subtype was wrong.

gcc/ada/

	* exp_attr.adb
	(Expand_Loop_Entry_Attribute):
	Ensure that Etype of the saved expression is set correctly.
Many aspects are (correctly) marked as GNAT-specific but nevertheless not
listed in the Implementation_Defined_Aspect array, so this aligns the two
sides and also removes Default_Initial_Condition and Object_Size from the
list, since they are defined in Ada 2022.

This also moves No_Controlled_Parts and No_Task_Parts to the subclass of
boolean aspects, and completes the list of nonoverridable aspects defined
in Ada 2022.

gcc/ada/

	* aspects.ads (Aspect_Id): Alphabetize, remove the GNAT tag from
	Default_Initial_Condition and Object_Size, move No_Controlled_Parts
	and No_Task_Parts to boolean subclass.
	(Nonoverridable_Aspect_Id): Add missing Ada 2022 aspects.
	(Implementation_Defined_Aspect): Add all missing aspects, remove
	Max_Entry_Queue_Length and Object_Size
	(Aspect_Argument): Remove specific entries for No_Controlled_Parts
	and No_Task_Parts, list boolean aspects last.
	(Is_Representation_Aspect ): Move boolean aspects last.
	(Aspect_Names): Alphabetize.
	* sem_ch13.adb (Analyze_Aspect_Disable_Controlled): Adjust.
	(Analyze_Aspect_Specifications): Move around processing for
	No_Controlled_Parts and No_Task_Parts.
	(Check_Aspect_At_Freeze_Point): Remove specific entries for
	No_Controlled_Parts and No_Task_Parts
Fixes typo in comments and 2 instances of bad indentation.

gcc/ada/

	* gcc-interface/decl.cc (gnat_to_gnu_entity): Typo fix.
	(gnat_to_gnu_component_type): Indent fix.
	* gcc-interface/gigi.h (build_call_alloc_dealloc): Typo fix.
	* gcc-interface/utils.cc (make_dummy_type): Typo fix.
	* gcc-interface/utils2.cc (gnat_protect_expr): Indent fix.
This prevents Gigi from creating null GCC thunks, i.e. thunks that have all
their internal parameters set to zero, replacing them with aliases.  They
can arise in degenerate cases and null thunks would trip on an assertion in
former_thunk_p when they are later optimized.

gcc/ada/

	PR ada/109817
	* gcc-interface/trans.cc (maybe_make_gnu_thunk): Create an alias
	instead of a null thunk.
Entities of kind E_Subprogram_Body, used on bodies of subprograms for
which there is a separate declaration, have been added in the entities
linked from a scope in order to get the representation information on
their enclosed object and type declarations. Skip these entities in gigi.

gcc/ada/

	* gcc-interface/trans.cc (elaborate_all_entities_for_package)
	(process_freeze_entity): Skip entities of kind E_Subprogram_Body.
The return mechanism of functions is reported when the -gnatRm switch is
specified, but it is incorrect when the result type is not a by-reference
type in the language sense but is nevertheless returned by reference.

gcc/ada/

	* gcc-interface/decl.cc: Include function.h.
	(gnat_to_gnu_param): Minor comment tweaks.
	(gnat_to_gnu_subprog_type): Take into account the default for the
	computation of the return mechanism.  Give a warning if a by-copy
	specified mechanism cannot be honored.
They are unused in this context.

gcc/ada/

	* gcc-interface/Makefile.in (tmake_file): Remove all references.
This apparently was missed when support for Interix was removed in 2016.

gcc:
	PR target/69374
	* doc/install.texi (Specific): Remove stale reference to Interix.
We have vec_extract pattern which takes ZVFHMIN as the mode
iterator of the V mode.  Aka VF_ZVFHMIN iterator.  But it will
expand to pred_extract_first pattern which takes the ZVFH as the mode
iterator of the V mode.  AKa VF.  The mismatch will result in one ICE
similar as below:

insn 30 29 31 2 (set (reg:HF 156 [ _2 ])
        (unspec:HF [
                (vec_select:HF (reg:RVVMF2HF 134 [ _1 ])
                    (parallel [
                            (const_int 0 [0])
                        ]))
                (reg:SI 67 vtype)
            ] UNSPEC_VPREDICATE)) "compress_run-2.c":22:3 -1
     (nil))
during RTL pass: vregs
compress_run-2.c:25:1: internal compiler error: in extract_insn, at
recog.cc:2812
0xb3bc47 _fatal_insn(char const*, rtx_def const*, char const*, int, char
const*)
        ../../../gcc/gcc/rtl-error.cc:108
0xb3bc69 _fatal_insn_not_found(rtx_def const*, char const*, int, char
const*)
        ../../../gcc/gcc/rtl-error.cc:116
0xb3a545 extract_insn(rtx_insn*)
        ../../../gcc/gcc/recog.cc:2812
0x1010e9e instantiate_virtual_regs_in_insn
        ../../../gcc/gcc/function.cc:1612
0x1010e9e instantiate_virtual_regs
        ../../../gcc/gcc/function.cc:1995
0x1010e9e execute
        ../../../gcc/gcc/function.cc:2042

The below test suites are passed for this patch.
1. The rv64gcv fully regression test.
2. The rv64gcv build with glibc.

There may be other similar issue(s) for the mismatch,  we will take care
of them by test cases one by one.

	PR target/115456

gcc/ChangeLog:

	* config/riscv/vector-iterators.md: Leverage V_ZVFH instead of V
	which contains the VF_ZVFHMIN for alignment.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/rvv/base/pr115456-2.c: New test.
	* gcc.target/riscv/rvv/base/pr115456-3.c: New test.

Signed-off-by: Pan Li <[email protected]>
gcc:
	* doc/invoke.texi (x86 Options): Consolidate duplicate MOVBE
	listings for haswell, broadwell, skylake, skylake-avx512,
	cannonlake, icelake-client, icelake-server, cascadelake,
	cooperlake, tigerlake, sapphirerapids, rocketlake, graniterapids,
	and graniterapids-d options to -march.
…tion

We can at least mimic single def-use cycle optimization when doing
single-lane SLP reductions and that's required to avoid regressing
compared to non-SLP.

	* tree-vect-loop.cc (vectorizable_reduction): Allow
	single-def-use cycles with SLP.
	(vect_transform_reduction): Handle SLP single def-use cycles.
	(vect_transform_cycle_phi): Likewise.

	* gcc.dg/vect/slp-reduc-12.c: New testcase.
The following disables SSE4 instead of just AVX to avoid
pextrq being used, confusing the assembler scanning.  This
avoids the reported failure with -march=cascadelake but adds
a FAIL for -march=cascadelake -m32 (I've opened PR115487 for that).

	* gcc.target/i386/vect-strided-3.c: Disable SSE4 instead of AVX.
For one setting ld_ver in a conditional (no in-tree ld) when it's used,
for x86 at least, in unconditional ways can't be quite right. And then
prefixing relative paths to binaries with ${objdir}/, when ${objdir}
nowadays resolves to just .libs, can at best be a leftover that wasn't
properly cleaned up at some earlier point.

gcc/

	* configure.ac: Drop ${objdir}/ from NM and AR. Move setting of
	ld_ver out of conditional.
	* configure: Re-generate.
After we support the scalar unsigned form 1 and 2,  we would like
to introduce more forms include the branch and branchless.  There
are forms 3-10 list as below:

Form 3:
  #define SAT_SUB_U_3(T) \
  T sat_sub_u_3_##T (T x, T y) \
  { \
    return x > y ? x - y : 0; \
  }

Form 4:
  #define SAT_SUB_U_4(T) \
  T sat_sub_u_4_##T (T x, T y) \
  { \
    return x >= y ? x - y : 0; \
  }

Form 5:
  #define SAT_SUB_U_5(T) \
  T sat_sub_u_5_##T (T x, T y) \
  { \
    return x < y ? 0 : x - y; \
  }

Form 6:
  #define SAT_SUB_U_6(T) \
  T sat_sub_u_6_##T (T x, T y) \
  { \
    return x <= y ? 0 : x - y; \
  }

Form 7:
  #define SAT_SUB_U_7(T) \
  T sat_sub_u_7_##T (T x, T y) \
  { \
    T ret; \
    T overflow = __builtin_sub_overflow (x, y, &ret); \
    return ret & (T)(overflow - 1); \
  }

Form 8:
  #define SAT_SUB_U_8(T) \
  T sat_sub_u_8_##T (T x, T y) \
  { \
    T ret; \
    T overflow = __builtin_sub_overflow (x, y, &ret); \
    return ret & (T)-(!overflow); \
  }

Form 9:
  #define SAT_SUB_U_9(T) \
  T sat_sub_u_9_##T (T x, T y) \
  { \
    T ret; \
    T overflow = __builtin_sub_overflow (x, y, &ret); \
    return overflow ? 0 : ret; \
  }

Form 10:
  #define SAT_SUB_U_10(T) \
  T sat_sub_u_10_##T (T x, T y) \
  { \
    T ret; \
    T overflow = __builtin_sub_overflow (x, y, &ret); \
    return !overflow ? ret : 0; \
  }

Take form 10 as example:

SAT_SUB_U_10(uint64_t);

Before this patch:
uint8_t sat_sub_u_10_uint8_t (uint8_t x, uint8_t y)
{
  unsigned char _1;
  unsigned char _2;
  uint8_t _3;
  __complex__ unsigned char _6;

;;   basic block 2, loop depth 0
;;    pred:       ENTRY
  _6 = .SUB_OVERFLOW (x_4(D), y_5(D));
  _2 = IMAGPART_EXPR <_6>;
  if (_2 == 0)
    goto <bb 3>; [50.00%]
  else
    goto <bb 4>; [50.00%]
;;    succ:       3
;;                4

;;   basic block 3, loop depth 0
;;    pred:       2
  _1 = REALPART_EXPR <_6>;
;;    succ:       4

;;   basic block 4, loop depth 0
;;    pred:       2
;;                3
  # _3 = PHI <0(2), _1(3)>
  return _3;
;;    succ:       EXIT

}

After this patch:
uint8_t sat_sub_u_10_uint8_t (uint8_t x, uint8_t y)
{
  uint8_t _3;

;;   basic block 2, loop depth 0
;;    pred:       ENTRY
  _3 = .SAT_SUB (x_4(D), y_5(D)); [tail call]
  return _3;
;;    succ:       EXIT

}

The below test suites are passed for this patch:
1. The rv64gcv fully regression test with newlib.
2. The rv64gcv build with glibc.
3. The x86 bootstrap test.
4. The x86 fully regression test.

gcc/ChangeLog:

	* match.pd: Add more match for unsigned sat_sub.
	* tree-ssa-math-opts.cc (match_unsigned_saturation_sub): Add new
	func impl to match phi node for .SAT_SUB.
	(math_opts_dom_walker::after_dom_children): Try match .SAT_SUB
	for the phi node, MULT_EXPR, BIT_XOR_EXPR and BIT_AND_EXPR.

Signed-off-by: Pan Li <[email protected]>
After the middle-end support the form 3 of unsigned SAT_SUB and
the RISC-V backend implement the scalar .SAT_SUB, add more test
case to cover the form 3 of unsigned .SAT_SUB.

Form 3:
  #define SAT_SUB_U_3(T) \
  T sat_sub_u_3_##T (T x, T y) \
  { \
    return x > y ? x - y : 0; \
  }

Passed the rv64gcv fully regression test.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/sat_arith.h: Add helper macro for test.
	* gcc.target/riscv/sat_u_sub-10.c: New test.
	* gcc.target/riscv/sat_u_sub-11.c: New test.
	* gcc.target/riscv/sat_u_sub-12.c: New test.
	* gcc.target/riscv/sat_u_sub-9.c: New test.
	* gcc.target/riscv/sat_u_sub-run-10.c: New test.
	* gcc.target/riscv/sat_u_sub-run-11.c: New test.
	* gcc.target/riscv/sat_u_sub-run-12.c: New test.
	* gcc.target/riscv/sat_u_sub-run-9.c: New test.

Signed-off-by: Pan Li <[email protected]>
After the middle-end support the form 4 of unsigned SAT_SUB and
the RISC-V backend implement the scalar .SAT_SUB, add more test
case to cover the form 4 of unsigned .SAT_SUB.

Form 4:
  #define SAT_SUB_U_4(T) \
  T sat_sub_u_4_##T (T x, T y) \
  { \
    return x >= y ? x - y : 0; \
  }

Passed the rv64gcv fully regression test.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/sat_arith.h: Add helper macro for test.
	* gcc.target/riscv/sat_u_sub-13.c: New test.
	* gcc.target/riscv/sat_u_sub-14.c: New test.
	* gcc.target/riscv/sat_u_sub-15.c: New test.
	* gcc.target/riscv/sat_u_sub-16.c: New test.
	* gcc.target/riscv/sat_u_sub-run-13.c: New test.
	* gcc.target/riscv/sat_u_sub-run-14.c: New test.
	* gcc.target/riscv/sat_u_sub-run-15.c: New test.
	* gcc.target/riscv/sat_u_sub-run-16.c: New test.

Signed-off-by: Pan Li <[email protected]>
After the middle-end support the form 5 of unsigned SAT_SUB and
the RISC-V backend implement the scalar .SAT_SUB, add more test
case to cover the form 5 of unsigned .SAT_SUB.

Form 5:
  #define SAT_SUB_U_5(T) \
  T sat_sub_u_5_##T (T x, T y) \
  { \
    return x < y ? 0 : x - y; \
  }

Passed the rv64gcv fully regression test.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/sat_arith.h: Add helper macro for test.
	* gcc.target/riscv/sat_u_sub-17.c: New test.
	* gcc.target/riscv/sat_u_sub-18.c: New test.
	* gcc.target/riscv/sat_u_sub-19.c: New test.
	* gcc.target/riscv/sat_u_sub-20.c: New test.
	* gcc.target/riscv/sat_u_sub-run-17.c: New test.
	* gcc.target/riscv/sat_u_sub-run-18.c: New test.
	* gcc.target/riscv/sat_u_sub-run-19.c: New test.
	* gcc.target/riscv/sat_u_sub-run-20.c: New test.

Signed-off-by: Pan Li <[email protected]>
After the middle-end support the form 6 of unsigned SAT_SUB and
the RISC-V backend implement the scalar .SAT_SUB, add more test
case to cover the form 6 of unsigned .SAT_SUB.

Form 6:
  #define SAT_SUB_U_6(T) \
  T sat_sub_u_6_##T (T x, T y) \
  { \
    return x <= y ? 0 : x - y; \
  }

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/sat_arith.h: Add helper macro for test.
	* gcc.target/riscv/sat_u_sub-21.c: New test.
	* gcc.target/riscv/sat_u_sub-22.c: New test.
	* gcc.target/riscv/sat_u_sub-23.c: New test.
	* gcc.target/riscv/sat_u_sub-24.c: New test.
	* gcc.target/riscv/sat_u_sub-run-21.c: New test.
	* gcc.target/riscv/sat_u_sub-run-22.c: New test.
	* gcc.target/riscv/sat_u_sub-run-23.c: New test.
	* gcc.target/riscv/sat_u_sub-run-24.c: New test.

Signed-off-by: Pan Li <[email protected]>
After the middle-end support the form 7 of unsigned SAT_SUB and
the RISC-V backend implement the scalar .SAT_SUB, add more test
case to cover the form 7 of unsigned .SAT_SUB.

Form 7:
  #define SAT_SUB_U_7(T) \
  T sat_sub_u_7_##T (T x, T y) \
  { \
    T ret; \
    T overflow = __builtin_sub_overflow (x, y, &ret); \
    return ret & (T)(overflow - 1); \
  }

Passed the rv64gcv fully regression test.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/sat_arith.h: Add helper macro for test.
	* gcc.target/riscv/sat_u_sub-25.c: New test.
	* gcc.target/riscv/sat_u_sub-26.c: New test.
	* gcc.target/riscv/sat_u_sub-27.c: New test.
	* gcc.target/riscv/sat_u_sub-28.c: New test.
	* gcc.target/riscv/sat_u_sub-run-25.c: New test.
	* gcc.target/riscv/sat_u_sub-run-26.c: New test.
	* gcc.target/riscv/sat_u_sub-run-27.c: New test.
	* gcc.target/riscv/sat_u_sub-run-28.c: New test.

Signed-off-by: Pan Li <[email protected]>
After the middle-end support the form 8 of unsigned SAT_SUB and
the RISC-V backend implement the scalar .SAT_SUB, add more test
case to cover the form 8 of unsigned .SAT_SUB.

Form 8:
  #define SAT_SUB_U_8(T) \
  T sat_sub_u_8_##T (T x, T y) \
  { \
    T ret; \
    T overflow = __builtin_sub_overflow (x, y, &ret); \
    return ret & (T)-(!overflow); \
  }

Passed the rv64gcv fully regression test.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/sat_arith.h: Add helper macro for test.
	* gcc.target/riscv/sat_u_sub-29.c: New test.
	* gcc.target/riscv/sat_u_sub-30.c: New test.
	* gcc.target/riscv/sat_u_sub-31.c: New test.
	* gcc.target/riscv/sat_u_sub-32.c: New test.
	* gcc.target/riscv/sat_u_sub-run-29.c: New test.
	* gcc.target/riscv/sat_u_sub-run-30.c: New test.
	* gcc.target/riscv/sat_u_sub-run-31.c: New test.
	* gcc.target/riscv/sat_u_sub-run-32.c: New test.

Signed-off-by: Pan Li <[email protected]>
After the middle-end support the form 9 of unsigned SAT_SUB and
the RISC-V backend implement the scalar .SAT_SUB, add more test
case to cover the form 9 of unsigned .SAT_SUB.

Form 9:
  #define SAT_SUB_U_9(T) \
  T sat_sub_u_9_##T (T x, T y) \
  { \
    T ret; \
    T overflow = __builtin_sub_overflow (x, y, &ret); \
    return overflow ? 0 : ret; \
  }

Passed the rv64gcv fully regression test.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/sat_arith.h: Add helper macro for test.
	* gcc.target/riscv/sat_u_sub-33.c: New test.
	* gcc.target/riscv/sat_u_sub-34.c: New test.
	* gcc.target/riscv/sat_u_sub-35.c: New test.
	* gcc.target/riscv/sat_u_sub-36.c: New test.
	* gcc.target/riscv/sat_u_sub-run-33.c: New test.
	* gcc.target/riscv/sat_u_sub-run-34.c: New test.
	* gcc.target/riscv/sat_u_sub-run-35.c: New test.
	* gcc.target/riscv/sat_u_sub-run-36.c: New test.

Signed-off-by: Pan Li <[email protected]>
After the middle-end support the form 10 of unsigned SAT_SUB and
the RISC-V backend implement the scalar .SAT_SUB, add more test
case to cover the form 10 of unsigned .SAT_SUB.

Form 10:
  #define SAT_SUB_U_10(T) \
  T sat_sub_u_10_##T (T x, T y) \
  { \
    T ret; \
    T overflow = __builtin_sub_overflow (x, y, &ret); \
    return !overflow ? ret : 0; \
  }

Passed the rv64gcv fully regression test.

gcc/testsuite/ChangeLog:

	* gcc.target/riscv/sat_arith.h: Add helper macro for test.
	* gcc.target/riscv/sat_u_sub-37.c: New test.
	* gcc.target/riscv/sat_u_sub-38.c: New test.
	* gcc.target/riscv/sat_u_sub-39.c: New test.
	* gcc.target/riscv/sat_u_sub-40.c: New test.
	* gcc.target/riscv/sat_u_sub-run-37.c: New test.
	* gcc.target/riscv/sat_u_sub-run-38.c: New test.
	* gcc.target/riscv/sat_u_sub-run-39.c: New test.
	* gcc.target/riscv/sat_u_sub-run-40.c: New test.

Signed-off-by: Pan Li <[email protected]>
rsandifo-arm and others added 30 commits June 21, 2024 09:52
*minus_plus_one had no constraints, which meant that it could be
matched after RA with operands 0, 1 and 2 all being different.
The associated split instead requires operand 0 to be tied to
operand 1.

gcc/
	* config/sh/sh.md (*minus_plus_one): Add constraints.
This fixes a warning from one of the test allocators:
warning: base class 'class std::allocator<__gnu_test::copy_tracker>' should be explicitly initialized in the copy constructor [-Wextra]

libstdc++-v3/ChangeLog:

	* testsuite/util/testsuite_allocator.h (tracker_allocator):
	Initialize base class in copy constructor.
Due to PR c++/85723 the std::is_trivial trait is true for types with a
deleted default constructor, so the use of std::is_trivial in
std::to_array is not sufficient to ensure the type can be trivially
default constructed then filled using memcpy.

I also forgot that a type with a deleted assignment operator can still
be trivial, so we also need to check that it's assignable because the
is_constant_evaluated() path can't use memcpy.

Replace the uses of std::is_trivial with std::is_trivially_copyable
(needed for memcpy), std::is_trivially_default_constructible (needed so
that the default construction is valid and does no work) and
std::is_copy_assignable (needed for the constant evaluation case).

libstdc++-v3/ChangeLog:

	PR libstdc++/115522
	* include/std/array (to_array): Workaround the fact that
	std::is_trivial is not sufficient to check that a type is
	trivially default constructible and assignable.
	* testsuite/23_containers/array/creation/115522.cc: New test.
The <chrono> header is incomplete for the old std::string ABI, because
std::chrono::tzdb is only defined for the new ABI. The feature test
macro advertising full C++20 support should not be defined for the old
ABI.

libstdc++-v3/ChangeLog:

	* include/bits/version.def (chrono): Add cxx11abi = yes.
	* include/bits/version.h: Regenerate.
	* testsuite/std/time/syn_c++20.cc: Adjust expected value for
	the feature test macro.
…r_convert

These were deprecated in C++17 and std::wstring_convert is planned for
removal in C++26.

libstdc++-v3/ChangeLog:

	* include/bits/locale_conv.h (wstring_convert): Add deprecated
	attribute for C++17 and later.
	(wbuffer_convert): Likewise.
	* testsuite/22_locale/codecvt/codecvt_utf16/79980.cc: Disable
	deprecated warnings.
	* testsuite/22_locale/codecvt/codecvt_utf8/79980.cc: Likewise.
	* testsuite/22_locale/codecvt/codecvt_utf8_utf16/79511.cc:
	Likewise.
	* testsuite/22_locale/conversions/buffer/1.cc: Add dg-warning.
	* testsuite/22_locale/conversions/buffer/2.cc: Likewise.
	* testsuite/22_locale/conversions/buffer/3.cc: Likewise.
	* testsuite/22_locale/conversions/buffer/requirements/typedefs.cc:
	Likewise.
	* testsuite/22_locale/conversions/string/1.cc: Likewise.
	* testsuite/22_locale/conversions/string/2.cc: Likewise.
	* testsuite/22_locale/conversions/string/3.cc: Likewise.
	* testsuite/22_locale/conversions/string/66441.cc: Likewise.
	* testsuite/22_locale/conversions/string/requirements/typedefs-2.cc:
	Likewise.
	* testsuite/22_locale/conversions/string/requirements/typedefs.cc:
	Likewise.
libstdc++-v3/ChangeLog:

	* include/backward/backward_warning.h: Adjust comments to
	suggest <spanstream> as another alternative to <strstream>.
	* include/backward/strstream (strstreambuf, istrstream)
	(ostrstream, strstream): Add deprecated attribute.
…5R4)

This member function was previously deprecated, but that was reverted by
P2875R4, approved earlier this year in Tokyo. Since it's not going to be
deprecated in C++26, and so presumably not removed, there is no point in
giving deprecated warnings for C++23 mode.

libstdc++-v3/ChangeLog:

	* include/bits/memory_resource.h (polymorphic_allocator::destroy):
	Remove deprecated attribute.
LWG 3305 was approved earlier this year in Tokyo. We need to give an
error if using std::any_cast<void>, but std::any_cast<void()> is valid
(but always returns null).

libstdc++-v3/ChangeLog:

	* include/std/any (any_cast(any*), any_cast(const any*)): Add
	static assertion to reject void types, as per LWG 3305.
	* testsuite/20_util/any/misc/lwg3305.cc: New test.
libstdc++-v3/ChangeLog:

	* include/bits/stl_uninitialized.h (uninitialized_default_construct)
	(uninitialized_default_construct_n, uninitialized_value_construct)
	(uninitialized_value_construct_n): Qualify calls to prevent ADL.
When adding validation of .sarif files against the schema
(PR testsuite/109360) I discovered various issues where we were
generating invalid .sarif files.

Specifically, in
  c-c++-common/diagnostic-format-sarif-file-bad-utf8-pr109098-1.c
the relatedLocations for the "note" diagnostics were missing column
numbers, leading to validation failure due to non-unique elements,
such as multiple:
	"message": {"text": "invalid UTF-8 character <bf>"}},
on line 25 with no column information.

Root cause is that for some diagnostics in libcpp we have a location_t
representing the line as a whole, setting a column_override on the
rich_location (since the line hasn't been fully read yet).  We were
handling this column override for plain text output, but not for .sarif
output.

Similarly, in diagnostic-format-sarif-file-pr111700.c there is a warning
emitted on "line 0" of the file, whereas SARIF requires line numbers to
be positive.

We also use column == 0 internally to mean "the line as a whole",
whereas SARIF required column numbers to be positive.

This patch fixes these various issues.

gcc/ChangeLog:
	PR testsuite/109360
	* diagnostic-format-sarif.cc
	(sarif_builder::make_location_object): Pass any column override
	from rich_loc to maybe_make_physical_location_object.
	(sarif_builder::maybe_make_physical_location_object): Add
	"column_override" param and pass it to maybe_make_region_object.
	(sarif_builder::maybe_make_region_object): Add "column_override"
	param and use it when the location has 0 for a column.  Don't
	add "startLine", "startColumn", "endLine", or "endColumn" if
	the values aren't positive.
	(sarif_builder::maybe_make_region_object_for_context): Don't
	add "startLine" or "endLine" if the values aren't positive.

libcpp/ChangeLog:
	PR testsuite/109360
	* include/rich-location.h (rich_location::get_column_override):
	New accessor.

Signed-off-by: David Malcolm <[email protected]>
…IF schema [PR109360]

This patch extends the dg directive verify-sarif-file so that if
the "jsonschema" tool is available, it will be used to validate the
generated .sarif file.

Tested with jsonschema 3.2 with Python 3.8

gcc/ChangeLog:
	PR testsuite/109360
	* doc/install.texi: Mention optional usage of "jsonschema" tool.

gcc/testsuite/ChangeLog:
	PR testsuite/109360
	* lib/sarif-schema-2.1.0.json: New file, downloaded from
	https://docs.oasis-open.org/sarif/sarif/v2.1.0/os/schemas/sarif-schema-2.1.0.json
	Licensing information can be seen at
	oasis-tcs/sarif-spec#583
	which states "They are free to incorporate it into their
	implementation. No need for special permission or paperwork from
	OASIS."
	* lib/scansarif.exp (verify-sarif-file): If "jsonschema" is
	available, use it to verify that the .sarif file complies with the
	SARIF schema.
	* lib/target-supports.exp (check_effective_target_jsonschema):
	New.

Signed-off-by: David Malcolm <[email protected]>
Add a remove_unreachable object to fast vrp, and honor the final_p flag.

	* tree-vrp.cc (remove_unreachable::remove): Export global range
	if builtin_unreachable dominates all uses.
	(remove_unreachable::remove_and_update_globals): Do not reset SCEV.
	(execute_ranger_vrp): Reset SCEV here instead.
	(fvrp_folder::fvrp_folder): Take final pass flag
	and create a remove_unreachable object when specified.
	(fvrp_folder::pre_fold_stmt): Register GIMPLE_CONDs with
	the remove_unreachcable object.
	(fvrp_folder::m_unreachable): New.
	(execute_fast_vrp): Process remove_unreachable object.
	(pass_vrp::execute): Add final_p flag to execute_fast_vrp.
Change the fast VRP algorithm to track contextual ranges active within
each basic block.

	* gimple-range.cc (dom_ranger::dom_ranger): Create a block
	vector.
	(dom_ranger::~dom_ranger): Dispose of the block vector.
	(dom_ranger::edge_range): Delete.
	(dom_ranger::range_on_edge): Combine range in src BB with any
	range gori_nme_on_edge returns.
	(dom_ranger::range_in_bb): Combine global range with any active
	contextual range for an ssa-name.
	(dom_ranger::range_of_stmt): Fix non-ssa LHS case, use
	fur_depend for folding so relations can be registered.
	(dom_ranger::maybe_push_edge): Delete.
	(dom_ranger::pre_bb): Create incoming contextual range vector.
	(dom_ranger::post_bb): Free contextual range vector.
	* gimple-range.h (dom_ranger::edge_range): Delete.
	(dom_ranger::m_e0): Delete.
	(dom_ranger::m_e1): Delete.
	(dom_ranger::m_bb): New.
	(dom_ranger::m_pop_list): Delete.
	* tree-vrp.cc (execute_fast_vrp): Enable relation oracle.
	* gimple-range.cc (gimple_ranger::register_inferred_ranges): Do not
	dump global range info after set_range_info.
	(gimple_ranger::register_transitive_inferred_ranges): Likewise.
	(dom_ranger::range_of_stmt): Likewise.
	* tree-ssanames.cc (set_range_info): If global range info
	changes, maybe print new range to dump_file.
	* tree-vrp.cc (remove_unreachable::handle_early): Do not
	dump global range info after set_range_info.
	(remove_unreachable::remove): Likewise.
	(remove_unreachable::remove_and_update_globals): Likewise.
	(pass_assumptions::execute): Likewise.
No-op moves are given the code NOOP_MOVE_INSN_CODE if we plan
to delete them later.  Such insns shouldn't be costed, partly
because they're going to disappear, and partly because targets
won't recognise the insn code.

gcc/
	* rtl-ssa/changes.cc (rtl_ssa::changes_are_worthwhile): Don't
	cost no-op moves.
	* rtl-ssa/insns.cc (insn_info::calculate_cost): Likewise.
The iq2000 test and branch instructions had patterns like:

  [(set (pc)
	(if_then_else
	 (eq (and:SI (match_operand:SI 0 "register_operand" "r")
		     (match_operand:SI 1 "power_of_2_operand" "I"))
	      (const_int 0))
	 (match_operand 2 "pc_or_label_operand" "")
	 (match_operand 3 "pc_or_label_operand" "")))]

power_of_2_operand allows any 32-bit power of 2, whereas "I" only
accepts 16-bit signed constants.  This meant that any power of 2
greater than 32768 would cause an "insn does not satisfy its
constraints" ICE.

Also, the %p operand modifier barfed on 1<<31, which is sign-
rather than zero-extended to 64 bits.  The code is inherently
limited to 32-bit operands -- power_of_2_operand contains a test
involving "unsigned" -- so this patch just ands with 0xffffffff.

gcc/
	* config/iq2000/iq2000.cc (iq2000_print_operand): Make %p handle 1<<31.
	* config/iq2000/iq2000.md: Remove "I" constraints on
	power_of_2_operands.
All uses of xs_hi_nonmemory_operand allow constraint "i",
which means that they allow consts, symbol_refs and label_refs.
The definition of xs_hi_nonmemory_operand accounted for consts,
but not for symbol_refs and label_refs.

gcc/
	* config/stormy16/predicates.md (xs_hi_nonmemory_operand): Handle
	symbol_ref and label_ref.
* Running a test compiled with AVX512 instructions requires
avx512f_runtime not just avx512f.

* The 'reduce2' test violated an invariant of fixed_size_simd_mask and
thus failed on all targets without 16-Byte vector builtins enabled (in
bits/simd.h).

Signed-off-by: Matthias Kretz <[email protected]>

libstdc++-v3/ChangeLog:

	PR libstdc++/115575
	* testsuite/experimental/simd/pr115454_find_last_set.cc: Require
	avx512f_runtime. Don't memcpy fixed_size masks.
As noted in the PR, the optimization used for scalar types in std::fill
and std::fill_n is non-conforming, because it doesn't consider that
assigning a scalar type might have non-trivial side effects which are
affected by the optimization.

By changing the condition under which the optimization is done we ensure
it's only performed when safe to do so, and we also enable it for
additional types, which was the original subject of the PR.

Instead of two overloads using __enable_if<__is_scalar<T>::__value, R>
we can combine them into one and create a local variable which is either
a local copy of __value or another reference to it, depending on whether
the optimization is allowed.

This removes a use of std::__is_scalar, which is a step towards fixing
PR 115497 by removing std::__is_pointer from <bits/cpp_type_traits.h>

libstdc++-v3/ChangeLog:

	PR libstdc++/109150
	* include/bits/stl_algobase.h (__fill_a1): Combine the
	!__is_scalar and __is_scalar overloads into one and rewrite the
	condition used to decide whether to perform the load outside the
	loop.
	* testsuite/25_algorithms/fill/109150.cc: New test.
	* testsuite/25_algorithms/fill_n/109150.cc: New test.
… [PR115497]

This removes the use of the std::__is_scalar trait from <valarray>,
where it can be replaced by __is_trivial. It's used to decide whether we
can use memset to value-initialize valarray elements, but memset is
suitable for any trivial types, because value-initializing them is
equivalent to filling them with zeros.

This is another step towards removing the class templates in
<bits/cpp_type_traits.h> that conflict with Clang built-in names.

libstdc++-v3/ChangeLog:

	PR libstdc++/115497
	* include/bits/valarray_array.h (__valarray_default_construct):
	Use __is_trivial(_Tp). instead of __is_scalar<_Tp>.
…R115497]

This replaces all uses of the std::__is_pointer type trait with uses of
the new __is_pointer built-in. Since the class template was only used to
enable some performance optimizations for algorithms, we can use the
built-in when __has_builtin(__is_pointer) is true (which is the case for
GCC trunk and for current versions of Clang) and just forego the
optimization otherwise.

Removing the uses of std::__is_pointer means it can be removed from
<bits/cpp_type_traits.h>, which is another step towards fixing PR
115497.

libstdc++-v3/ChangeLog:

	PR libstdc++/115497
	* include/bits/deque.tcc (__lex_cmp_dit): Replace __is_pointer
	class template with __is_pointer(T) built-in.
	(__lexicographical_compare_aux1): Likewise.
	* include/bits/stl_algobase.h (__equal_aux1): Likewise.
	(__lexicographical_compare_aux1): Likewise.
This removes the std::__is_void trait, as it conflicts with a Clang
built-in. There is only one use of the trait, which can easily be
replaced by simpler code.

Although Clang has a hack to make the class template work despite using
a reserved name, removing std::__is_void will allow that hack to be
dropped at some future date.

libstdc++-v3/ChangeLog:

	PR libstdc++/115497
	* include/bits/cpp_type_traits.h (__is_void): Remove.
	* include/debug/helper_functions.h (_Distance_traits):
	Adjust partial specialization to match void directly, instead of
	using __is_void<T>::__type and matching __true_type.
This removes the std::__is_pointer and std::__is_scalar traits, as they
conflicts with a Clang built-in.

Although Clang has a hack to make the class templates work despite using
reserved names, removing these class templates will allow that hack to
be dropped at some future date.

libstdc++-v3/ChangeLog:

	PR libstdc++/115497
	* include/bits/cpp_type_traits.h (__is_pointer, __is_scalar):
	Remove.
	(__is_arithmetic): Do not use __is_pointer in the primary
	template. Add partial specialization for pointers.
More minor fallout from the IOR->PLUS change a little while ago.  This time on
xstormy16.

The pattern to swap nibbles actually tries to handle all the cases of IOR, XOR
and PLUS.  But when we generate PLUS earlier in the pipeline, the
simplifications/canonicalizations are slightly different resulting in the
pattern not matching.

This patch adds an alternate pattern which matches what we get now.  Basically
it looks like QImode rotate by 4, zero extended to HI.

Run in my tester to verify the regression was fixed.  Pushing to the trunk.

gcc/
	* config/stormy16/stormy16.md (swpn_zext): New pattern.
…h.cc

No functional change intended.

gcc/ChangeLog:
	* diagnostic-path.cc (diagnostic_event::meaning::dump_to_pp): Move
	here from diagnostic.cc.
	(diagnostic_event::meaning::maybe_get_verb_str): Likewise.
	(diagnostic_event::meaning::maybe_get_noun_str): Likewise.
	(diagnostic_event::meaning::maybe_get_property_str): Likewise.
	(diagnostic_path::get_first_event_in_a_function): Likewise.
	(diagnostic_path::interprocedural_p): Likewise.
	(debug): Likewise for diagnostic_path * overload.
	* diagnostic.cc (diagnostic_event::meaning::dump_to_pp): Move from
	here to diagnostic-path.cc.
	(diagnostic_event::meaning::maybe_get_verb_str): Likewise.
	(diagnostic_event::meaning::maybe_get_noun_str): Likewise.
	(diagnostic_event::meaning::maybe_get_property_str): Likewise.
	(diagnostic_path::get_first_event_in_a_function): Likewise.
	(diagnostic_path::interprocedural_p): Likewise.
	(debug): Likewise for diagnostic_path * overload.

Signed-off-by: David Malcolm <[email protected]>
No functional change intended.

gcc/ChangeLog:
	* diagnostic-format-json.cc
	(json_output_format::on_end_diagnostic): Use
	get_diagnostic_kind_text rather than embedding a duplicate copy of
	the table.
	* diagnostic-format-sarif.cc
	(make_rule_id_for_diagnostic_kind): Likewise.
	* diagnostic.cc (get_diagnostic_kind_text): New.
	* diagnostic.h (get_diagnostic_kind_text): New decl.

Signed-off-by: David Malcolm <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.