aboutsummaryrefslogtreecommitdiff
path: root/doc
diff options
context:
space:
mode:
Diffstat (limited to 'doc')
-rw-r--r--doc/language/cpsc-language-overview.7.md7
-rw-r--r--doc/language/keyword/cpsc-keyword-c_type.7.md4
-rw-r--r--doc/language/keyword/cpsc-keyword-class.7.md2
-rw-r--r--doc/language/keyword/cpsc-keyword-constant.7.md2
-rw-r--r--doc/language/keyword/cpsc-keyword-implicit.7.md43
-rw-r--r--doc/language/keyword/cpsc-keyword-operator.7.md2
-rw-r--r--doc/language/keyword/cpsc-keyword-overload.7.md6
-rw-r--r--doc/language/keyword/cpsc-keyword-template.7.md4
8 files changed, 58 insertions, 12 deletions
diff --git a/doc/language/cpsc-language-overview.7.md b/doc/language/cpsc-language-overview.7.md
index da4d821..65d1945 100644
--- a/doc/language/cpsc-language-overview.7.md
+++ b/doc/language/cpsc-language-overview.7.md
@@ -14,9 +14,9 @@ User-defined types can overload operators with OVERLOAD FUNCTION OPERATOR; expre
Precedence, from highest to lowest: unary operators, `* / DIV MOD`, `+ - &`, comparisons, AND, OR. Parentheses override precedence.
-Parenthesized type casts, such as (C_INT)Number, have unary precedence. C_INT, C_CHAR, C_STRING and C_DOUBLE are native C aliases; TYPE name = C_TYPE("...") imports other supported C base types and pointers. Conversions between C and pseudocode types must be explicit. These are compiler extensions; see [cpsc-keyword-c_type(7)](keyword/cpsc-keyword-c_type.7.md). EXTERN "C" declares C functions from objects named with INCLUDE_OBJ; see [cpsc-keyword-extern(7)](keyword/cpsc-keyword-extern.7.md).
+Parenthesized type casts, such as (C_INT)Number, have unary precedence. C_INT, C_CHAR, C_STRING and C_DOUBLE are native C aliases; TYPE name = C_TYPE("...") imports other supported C base types and pointers. Conversions between C and pseudocode types require explicit casts except for IMPLICIT class constructors and the text bridges described below. These are compiler extensions; see [cpsc-keyword-c_type(7)](keyword/cpsc-keyword-c_type.7.md). EXTERN "C" declares C functions from objects named with INCLUDE_OBJ; see [cpsc-keyword-extern(7)](keyword/cpsc-keyword-extern.7.md).
-Literals include integers, decimal real numbers, TRUE/FALSE, strings in double quotes, and single-byte characters in single quotes. Negative numbers use unary minus. String and character literals support C++17 simple escapes (`\' \" \? \\ \a \b \f \n \r \t \v`), one to three octal digits, and `\x` followed by hexadecimal digits (byte values only). Unicode escapes `\uXXXX` and `\UXXXXXXXX` encode valid Unicode scalar values as UTF-8 in strings; in CHAR they must be ASCII. Unknown escapes are errors. Ordinary STRING literals retain NUL truncation, so `"a\0b"` is observed as `"a"`. An adjacent uppercase C suffix, as in `"text"C`, produces C_STRING directly. Comments begin with `//` and continue to the end of the line.
+Literals include integers, decimal real numbers, TRUE/FALSE, strings in double quotes, and single-byte characters in single quotes. Negative numbers use unary minus. String and character literals support C++17 simple escapes (`\' \" \? \\ \a \b \f \n \r \t \v`), one to three octal digits, and `\x` followed by hexadecimal digits (byte values only). Unicode escapes `\uXXXX` and `\UXXXXXXXX` encode valid Unicode scalar values as UTF-8 in strings; in CHAR they must be ASCII. Unknown escapes are errors. String literals have type C_STRING and retain NUL truncation in text operations, so `"a\0b"` is observed as `"a"`. An adjacent uppercase C suffix, as in `"text"C`, remains accepted and has the same type. The standard library converts text to STRING through IMPLICIT NEW when needed; see [cpsc-keyword-implicit(7)](keyword/cpsc-keyword-implicit.7.md). Comments begin with `//` and continue to the end of the line.
Declare variables before use. See DECLARE for built-in types and arrays, TYPE for records/enumerations/pointers, and CLASS for public/private fields and methods.
@@ -47,6 +47,7 @@ PP_DEFINE and PP_UNDEF control file-local, case-sensitive preprocessor switches.
- [cpsc-keyword-procedure(7)](keyword/cpsc-keyword-procedure.7.md): define a procedure and parameter modes.
- [cpsc-keyword-operator(7)](keyword/cpsc-keyword-operator.7.md): overload unary and binary operators.
- [cpsc-keyword-overload(7)](keyword/cpsc-keyword-overload.7.md): explicitly overload functions, procedures and constructors.
+- [cpsc-keyword-implicit(7)](keyword/cpsc-keyword-implicit.7.md): permit automatic class construction from one parameter.
- [cpsc-keyword-default(7)](keyword/cpsc-keyword-default.7.md): choose a default return type for an overload.
- [cpsc-keyword-template(7)](keyword/cpsc-keyword-template.7.md): define function, procedure and class templates with type packs.
- [cpsc-keyword-call(7)](keyword/cpsc-keyword-call.7.md): invoke a procedure.
@@ -70,7 +71,7 @@ Closing and auxiliary keywords are documented with their main constructs: PP_UND
# STRING LIBRARY FUNCTIONS
-These ordinary functions and the STRING class come from the embedded standard library, loaded and linked automatically unless **-no-std** is given. Ordinary string literals require a visible STRING class.
+These ordinary functions and the STRING class come from the embedded standard library, loaded and linked automatically unless **-no-std** is given. Using raw text in a STRING context, OUTPUT or file operation requires a visible STRING class with an IMPLICIT NEW(C_STRING) constructor.
- [cpsc-function-length(7)](function/cpsc-function-length.7.md): find a string's length.
- [cpsc-function-mid(7)](function/cpsc-function-mid.7.md): extract part of a string.
diff --git a/doc/language/keyword/cpsc-keyword-c_type.7.md b/doc/language/keyword/cpsc-keyword-c_type.7.md
index beff643..3b8f65c 100644
--- a/doc/language/keyword/cpsc-keyword-c_type.7.md
+++ b/doc/language/keyword/cpsc-keyword-c_type.7.md
@@ -21,9 +21,9 @@ C widths, char signedness and floating-point formats come from the compiler's bu
A cast has unary precedence and converts its following operand. Declare a type alias before using its name in a cast. Numeric, character and boolean values can be explicitly converted between pseudocode and C types. STRING can be cast to char* and back, and C pointer types can be cast to other C pointer types. C void* and original pseudocode pointer types can be explicitly cast to each other. Pointer/integer casts and casts involving pseudocode enums or whole records are unsupported. Casts are values, not assignable locations.
-C/pseudocode assignment, argument passing and mixed arithmetic require an explicit cast, including ordinary literals: use n <- (C_INT)1 and n + (C_INT)1. Different C scalar types use C++ numeric conversions, integer promotions and usual arithmetic conversions. BYREF requires the same type and performs no conversion. Comparisons and logical operations return BOOLEAN. The / operator always performs real division and returns REAL, including with two C integer operands; DIV and MOD accept C integers after promotion. C values used directly as IF/WHILE conditions need a cast to BOOLEAN.
+Except for marked IMPLICIT class constructors and the text bridges below, C/pseudocode assignment, argument passing and mixed arithmetic require an explicit cast, including numeric literals: use n <- (C_INT)1 and n + (C_INT)1. Different C scalar types use C++ numeric conversions, integer promotions and usual arithmetic conversions. BYREF requires the same type and performs no conversion. Comparisons and logical operations return BOOLEAN. The / operator always performs real division and returns REAL, including with two C integer operands; DIV and MOD accept C integers after promotion. C values used directly as IF/WHILE conditions need a cast to BOOLEAN.
-C scalar values support INPUT and OUTPUT. Plain char prints and reads a character; signed char and unsigned char use numeric input/output. _Bool uses the existing TRUE/FALSE output and numeric input. C pointers start null and support prefix ^ for address-of, suffix ^ for dereference, and = or <> between the same C pointer type. Dereferencing null throws; void pointers cannot be dereferenced. Pointer arithmetic and direct pointer INPUT/OUTPUT are unsupported. To print a C string, cast it to STRING. Casting char* to STRING constructs an owning copy; a null char* becomes empty. Casting STRING to char* borrows its buffer until the string changes or is destroyed. A literal such as `"text"C` has type C_STRING without constructing STRING. Pointer validity and writable storage remain the caller's responsibility.
+C scalar values support INPUT and OUTPUT. Plain char prints and reads a character; signed char and unsigned char use numeric input/output. _Bool uses the existing TRUE/FALSE output and numeric input. C pointers start null and support prefix ^ for address-of, suffix ^ for dereference, and = or <> between the same C pointer type. Dereferencing null throws; void pointers cannot be dereferenced. Pointer arithmetic and direct pointer INPUT/OUTPUT are unsupported, except that C_STRING output constructs STRING through its IMPLICIT constructor. Both ordinary and C-suffixed string literals have type C_STRING; they pass directly to C functions and select an exact C_STRING overload ahead of STRING conversion. Casting char* to STRING constructs an owning copy; a null char* becomes empty. Casting STRING to char* borrows its buffer until the string changes or is destroyed. A literal such as `"text"C` has type C_STRING without constructing STRING. Pointer validity and writable storage remain the caller's responsibility.
# EXAMPLE
diff --git a/doc/language/keyword/cpsc-keyword-class.7.md b/doc/language/keyword/cpsc-keyword-class.7.md
index 2a713c0..6d730aa 100644
--- a/doc/language/keyword/cpsc-keyword-class.7.md
+++ b/doc/language/keyword/cpsc-keyword-class.7.md
@@ -40,6 +40,8 @@ A constructor is a PROCEDURE named NEW, following guide section 10.2. It may be
`DECLARE Object : ClassName` zeroes the object's storage and constructs its fields recursively in declaration order; it then calls NEW only when the class has a parameterless NEW. Otherwise the object stays unconstructed until `Object <- NEW ClassName(arguments)` binds it, as in guide section 10.2. `DECLARE Object : ClassName(arguments)` always calls the matching NEW, so `ClassName()` is an error for a class whose NEW requires arguments, and supplying arguments to a class without NEW is an error. These automatic DECLARE, field and array calls are compiler extensions. Array elements and class-valued fields in records or classes follow the plain DECLARE rule, before the enclosing constructor runs. Constructor arguments after ARRAY OF are unsupported. A declaration executed again, such as inside a loop, first destroys its previous live incarnation, then zeroes and constructs its original storage again.
+A single-parameter BYVAL constructor may specify IMPLICIT to allow automatic conversion from its parameter type; see [cpsc-keyword-implicit(7)](cpsc-keyword-implicit.7.md).
+
An `OVERLOAD PROCEDURE NEW(BYREF Other : ClassName)` defines a copy constructor. BYVAL class lvalue arguments and RETURN of class lvalues invoke it; a same-class BYVAL constructor is rejected. Classes without one retain bitwise copying for fields without STRING ownership. Records and BYVAL arrays recursively clone STRING-bearing fields or elements. Other owning class fields retain the existing shallow-copy limitations. Class results transfer ownership directly into BYVAL arguments, RETURN and ordinary assignment without an assignment overload. Discarded results and temporary receivers live until the statement ends, including exception exits. Ordinary user BYREF calls still require bare variables; constructor calls can bind temporaries.
The keyword NEW is allowed only as the complete right side of assignment: `Target <- NEW ClassName`, `Target <- NEW ClassName()` or `Target <- NEW ClassName(arguments)`. Target must have exactly the named class type. NEW requires the memory.cps standard-library unit, imported by default; with **-no-std**, import and supply it explicitly. NEW uses the checked MALLOC allocation path, zeroes storage and constructs fields before calling NEW. A method-only class receives at least one byte of heap storage so its object address is non-null. Allocation failure reports a runtime error and throws; constructor exceptions also propagate to TRY/CATCH. Private constructor access and argument checks follow ordinary member-call rules.
diff --git a/doc/language/keyword/cpsc-keyword-constant.7.md b/doc/language/keyword/cpsc-keyword-constant.7.md
index 55960c5..5f1b9ad 100644
--- a/doc/language/keyword/cpsc-keyword-constant.7.md
+++ b/doc/language/keyword/cpsc-keyword-constant.7.md
@@ -12,7 +12,7 @@ CONSTANT identifier = literal
# DESCRIPTION
-Declare a read-only value whose type is inferred from its literal: INTEGER, REAL, BOOLEAN, CHAR, STRING, or C_STRING for a literal with the C suffix. A negative integer or real literal is allowed. As required by the Cambridge guide, variables, other constants, expressions, casts, and function calls cannot initialize a CONSTANT.
+Declare a read-only value whose type is inferred from its literal: INTEGER, REAL, BOOLEAN, CHAR or C_STRING. Both ordinary and C-suffixed double-quoted literals produce C_STRING; STRING contexts use its IMPLICIT constructor. A negative integer or real literal is allowed. As required by the Cambridge guide, variables, other constants, expressions, casts, and function calls cannot initialize a CONSTANT.
A constant is visible from its declaration to the end of its enclosing block. A top-level constant is also available in functions and procedures defined after its declaration. Functions do not inherit constants from another function or from an enclosing statement block.
diff --git a/doc/language/keyword/cpsc-keyword-implicit.7.md b/doc/language/keyword/cpsc-keyword-implicit.7.md
new file mode 100644
index 0000000..68d7283
--- /dev/null
+++ b/doc/language/keyword/cpsc-keyword-implicit.7.md
@@ -0,0 +1,43 @@
+% CPSC-KEYWORD-IMPLICIT(7)
+
+# NAME
+
+cpsc-keyword-implicit - allow automatic construction of a class value
+
+# SYNOPSIS
+
+```text
+CLASS name
+ [PUBLIC|PRIVATE] [OVERLOAD] IMPLICIT PROCEDURE NEW(value : type)
+ statements
+ ENDPROCEDURE
+ENDCLASS
+```
+
+# DESCRIPTION
+
+IMPLICIT is a compiler extension, absent from the CIE guide. Place it before PROCEDURE NEW, after OVERLOAD when present. The constructor must take exactly one BYVAL parameter, which may omit the BYVAL keyword. BYREF, array and parameter-pack parameters are rejected. Other methods and global functions cannot be IMPLICIT.
+
+A marked constructor allows its parameter type to become the owning class type in assignment, BYVAL argument passing, RETURN and overload selection. The parameter must match the source type directly; equivalent C aliases count as the same type. Conversion does not chain through another IMPLICIT constructor. Unmarked constructors remain available for explicit construction. No standard-library exception grants an unmarked constructor automatic conversion.
+
+Exact parameter matches take priority. If none matches, functions and operators may use implicit construction; competing candidates at the same level are ambiguous. PRIVATE access is checked after selection. BYREF parameters and whole arrays never convert. Existing result-type and DEFAULT selection rules still apply; see [cpsc-keyword-overload(7)](cpsc-keyword-overload.7.md). Directly supported built-in operations precede converted operators.
+
+Double-quoted literals and their CONSTANT values have type C_STRING. The standard library supplies IMPLICIT STRING constructors for C_STRING and CHAR. String functions, comparisons and concatenation therefore retain their normal text behavior. OUTPUT and file operations also bridge raw text through the marked STRING constructor. The older STRING-to-CHAR conversion checks for exactly one character; raw text can use this bridge after constructing STRING, with lower priority than a direct STRING parameter. The adjacent C suffix remains accepted and has the same C_STRING type.
+
+# EXAMPLE
+
+```text
+CLASS Box
+ Value : INTEGER
+ IMPLICIT PROCEDURE NEW(Number : INTEGER)
+ Value <- Number
+ ENDPROCEDURE
+ENDCLASS
+DECLARE Item : Box
+Item <- 42
+OUTPUT Item.Value
+```
+
+# SEE ALSO
+
+[cpsc-keyword-class(7)](cpsc-keyword-class.7.md), [cpsc-keyword-overload(7)](cpsc-keyword-overload.7.md), [cpsc-keyword-operator(7)](cpsc-keyword-operator.7.md), [cpsc-keyword-c_type(7)](cpsc-keyword-c_type.7.md).
diff --git a/doc/language/keyword/cpsc-keyword-operator.7.md b/doc/language/keyword/cpsc-keyword-operator.7.md
index 6c29370..134d3f2 100644
--- a/doc/language/keyword/cpsc-keyword-operator.7.md
+++ b/doc/language/keyword/cpsc-keyword-operator.7.md
@@ -29,7 +29,7 @@ OPERATOR is a compiler extension, absent from the CIE guide. Declare unary and b
Binary operators are `+ - * / DIV MOD & = <> < <= > >= AND OR`. Unary operators are `- NOT`. A global binary definition takes two parameters and a unary definition takes one; at least one parameter must be a record, class or enum. A pointer alias alone does not qualify. A member binary definition takes one explicit parameter and a unary definition takes none; this supplies the left or sole operand. PUBLIC and PRIVATE precede OVERLOAD as for other methods.
-Operands match exact static types, without implicit conversions, following OVERLOAD rules. For example, an INTEGER operand does not match a REAL parameter. Visible global definitions and methods of the left operand's class participate together. The selected method must be accessible: PRIVATE never causes a public fallback. Included units provide operators using the ordinary INCLUDE visibility rules.
+Operands prefer exact static types, following OVERLOAD rules. When no exact candidate or directly supported built-in operation applies, BYVAL operands may use IMPLICIT constructors; see [cpsc-keyword-implicit(7)](cpsc-keyword-implicit.7.md). For example, an INTEGER operand does not match a REAL parameter. Visible global definitions and methods of the left operand's class participate together. The selected method must be accessible: PRIVATE never causes a public fallback. Included units provide operators using the ordinary INCLUDE visibility rules.
Return types also distinguish operator overloads. When the context requires a result type (assignment, RETURN, condition, CASE comparison, subscript and similar positions), only definitions returning exactly that type match; if the operands match but no result does, the error is `No matching overload for OPERATOR +(T, U) returning R`. A cast `(R) expr` only prefers R and otherwise selects by operands before converting. Without an expected result type, such as OUTPUT or an operand of another operator, a unique operand match is selected; definitions that differ only by return type need a `RETURNS DEFAULT type` declaration to avoid ambiguity. DEFAULT follows the same rules as ordinary functions and does not resolve global/member operator ties; see [cpsc-keyword-default(7)](cpsc-keyword-default.7.md).
diff --git a/doc/language/keyword/cpsc-keyword-overload.7.md b/doc/language/keyword/cpsc-keyword-overload.7.md
index 1f7a0a4..bfd4ece 100644
--- a/doc/language/keyword/cpsc-keyword-overload.7.md
+++ b/doc/language/keyword/cpsc-keyword-overload.7.md
@@ -22,11 +22,11 @@ ENDCLASS
# DESCRIPTION
-OVERLOAD is a compiler extension, absent from the CIE guide. Put it immediately before FUNCTION or PROCEDURE, after PUBLIC or PRIVATE when an access keyword is present. OVERLOAD is reserved. Every definition sharing a case-insensitive name must specify OVERLOAD. Global functions, procedures, class methods and NEW constructors support it; MAIN and built-in functions do not.
+OVERLOAD is a compiler extension, absent from the CIE guide. Put it before FUNCTION or PROCEDURE, after PUBLIC or PRIVATE when an access keyword is present. An implicit constructor places IMPLICIT between OVERLOAD and PROCEDURE. OVERLOAD is reserved. Every definition sharing a case-insensitive name must specify OVERLOAD. Global functions, procedures, class methods and NEW constructors support it; MAIN and built-in functions do not.
Signatures differ by parameter count, parameter types, array rank, or return type. BYREF versus BYVAL and declared array bounds do not distinguish signatures. A PROCEDURE counts as returning VOID, so it can coexist with a FUNCTION having the same parameter list; a call that cannot determine a result type is then ambiguous unless the function specifies a DEFAULT return. Nominal user types remain distinct; equivalent native C type aliases identify the same type.
-Calls require an exact match to the arguments' static types. No implicit conversion is used to select an overload, even when only one OVERLOAD definition exists. Array arguments must be whole array variables with matching element types and rank. After selection, ordinary parameter-mode, array-bound and access checks apply. Functions without OVERLOAD retain their ordinary argument conversions and their implicit result conversions.
+Calls prefer exact static parameter types. If no exact candidate matches, BYVAL parameters may use a single IMPLICIT constructor or the existing CHAR/STRING bridge. Competing converted candidates are ambiguous; numeric widening does not select an overload. See [cpsc-keyword-implicit(7)](cpsc-keyword-implicit.7.md). Array arguments must be whole array variables with matching element types and rank. After selection, ordinary parameter-mode, array-bound and access checks apply. Functions without OVERLOAD retain their ordinary argument conversions and their implicit result conversions.
When the context requires a known result type, the selected overload must return exactly that type. This applies to assignment targets, BYVAL arguments, RETURN values, conditions, FOR bounds, subscripts and CASE comparisons. If the arguments match but no overload returns the required type, the error is `No matching overload for Name(T1, T2) returning T`. A cast `(T) expr` is weaker: it first prefers an overload returning T, then uses ordinary parameter selection and converts the result to T.
@@ -36,7 +36,7 @@ Overloads may be defined in separate input files. A caller sees only its own and
Methods use the same rules, including result-type selection; fields and methods cannot share a name. Constructor calls select NEW by their explicit arguments. DECLARE without arguments, class-valued fields and array elements select a parameterless NEW; if NEW exists but has no matching parameterless overload, compilation fails. PRIVATE checks apply to the selected method or constructor.
-Operator definitions use OVERLOAD FUNCTION OPERATOR followed by the operator symbol or keyword. They support global and member forms with exact operand types; see [cpsc-keyword-operator(7)](cpsc-keyword-operator.7.md).
+Operator definitions use OVERLOAD FUNCTION OPERATOR followed by the operator symbol or keyword. They support global and member forms with exact types preferred over implicit construction; see [cpsc-keyword-operator(7)](cpsc-keyword-operator.7.md).
# EXAMPLE
diff --git a/doc/language/keyword/cpsc-keyword-template.7.md b/doc/language/keyword/cpsc-keyword-template.7.md
index afa9cba..59cf889 100644
--- a/doc/language/keyword/cpsc-keyword-template.7.md
+++ b/doc/language/keyword/cpsc-keyword-template.7.md
@@ -25,11 +25,11 @@ ENDCLASS
TEMPLATE is a compiler extension, absent from the CIE guide. Place it before a top-level FUNCTION, PROCEDURE or CLASS, before OVERLOAD when present. Every template parameter names a type; no typename keyword is needed. Names must be distinct. A single optional type pack, written `Rest...`, must come last. Each concrete use creates and caches an ordinary function or class instance by substituting types into the template body.
-Function calls deduce types from parameters typed `T` or `ARRAY OF T`; bounded array parameters also require matching rank. Deduction does not look inside `Box<T>`. Explicit arguments, as in `Max<REAL>(1.5, 2.0)`, bind types positionally before deduction fills any remaining parameters. All argument types must match exactly, including explicitly bound types: `Max<REAL>(1, 2.5)` is an error. Explicit arguments are forbidden on ordinary functions and builtins. A type used only in RETURNS requires an explicit argument.
+Function calls deduce types from parameters typed `T` or `ARRAY OF T`; bounded array parameters also require matching rank. Deduction does not look inside `Box<T>`. Explicit arguments, as in `Max<REAL>(1.5, 2.0)`, bind types positionally before deduction fills any remaining parameters. Substituted BYVAL parameters may use IMPLICIT constructors or the existing CHAR/STRING bridge; otherwise types must match exactly, including explicitly bound types: `Max<REAL>(1, 2.5)` is an error. Explicit arguments are forbidden on ordinary functions and builtins. A type used only in RETURNS requires an explicit argument.
A final parameter `Others : Rest...` expands into one parameter per pack type, possibly none. It cannot be an ARRAY parameter. Write `Others...` only in argument lists of function or method calls, NEW or DECLARE constructors. A bare pack value is invalid. In type argument lists, `Rest...` forwards the current type pack. Explicit pack arguments constrain a prefix; deduction can supply the remaining types.
-When multiple function or procedure definitions share a name, every definition, including ordinary definitions, must specify OVERLOAD. Selection prefers an exact ordinary definition, then a non-variadic template, then a variadic template. Expected result types filter ordinary definitions but do not participate in template selection, which still matches substituted parameter types only. Two matches at the same level are ambiguous; no further template ordering is performed. Explicit template arguments select only templates. Normal BYREF, array-bound and access checks apply after selection; see [cpsc-keyword-overload(7)](cpsc-keyword-overload.7.md).
+When multiple function or procedure definitions share a name, every definition, including ordinary definitions, must specify OVERLOAD. Selection prefers an exact ordinary definition, then an exact non-variadic template, then an exact variadic template. If none matches, it repeats those levels with permitted implicit conversions. Expected result types filter ordinary definitions but do not participate in template selection, which still matches substituted parameter types only. Two matches at the same level are ambiguous; no further template ordering is performed. Explicit template arguments select only templates. Normal BYREF, array-bound and access checks apply after selection; see [cpsc-keyword-overload(7)](cpsc-keyword-overload.7.md).
Use a class instance such as `Box<INTEGER>` wherever a type name is accepted, including nested instances such as `Box<Box<INTEGER>>`. Supply all class type arguments explicitly; variadic CLASS templates are allowed, and their methods may use the class's pack parameters. Pack fields such as `Values : Rest...` are rejected. Constructors, ownership and destruction follow ordinary CLASS rules. In particular, a declaration without constructor arguments needs a matching parameterless NEW when constructors exist; see [cpsc-keyword-class(7)](cpsc-keyword-class.7.md).