|
| 1 | +To: J3 J3/24-116 |
| 2 | +From: Thomas Koenig and JoR |
| 3 | +Subject: A modest proposal for adding an UNSIGNED type to Fortran (DIN 6) |
| 4 | +Date: 2024-February-28 |
| 5 | + |
| 6 | +References: 24-102, 07-007 |
| 7 | + WG5 N2230 DIN Suggestions for F202Y.pdf |
| 8 | + WG5 N2142 Fortran 2020 Feature Survey Results 201710.pdf |
| 9 | + |
| 10 | +# 1. Introduction |
| 11 | + |
| 12 | +Unsigned integers are a basic data type used in many programming |
| 13 | +languages, such as C. Arithmetic on them is typically performed modulo |
| 14 | +2^n for a datatype with n bits. They are useful for a range of |
| 15 | +applications, including, but not limited to |
| 16 | + |
| 17 | +- hashing |
| 18 | +- cryptography (including multi-precision arithmetic) |
| 19 | +- image processing |
| 20 | +- signal processing |
| 21 | +- data compression |
| 22 | +- binary file I/O |
| 23 | +- interfacing to C |
| 24 | +- interfacing to the operating system |
| 25 | + |
| 26 | +Unsigned integers were the fourth most requested item to add to |
| 27 | +Fortran 202x in 2017. It is the sixth item on the DIN national body |
| 28 | +list for inclusion in Fortran 202y. |
| 29 | + |
| 30 | +We propose adding a small set of features for an unsigned data to |
| 31 | +Fortran 202y. |
| 32 | + |
| 33 | +## 1.1. Prior art |
| 34 | + |
| 35 | +At least one Fortran compiler, Sun Fortran, supported unsigned integers. |
| 36 | +Documentation can be found at [Oracle] |
| 37 | +(https://docs.oracle.com/cd/E19205-01/819-5263/aevnb/index.html). |
| 38 | +This proposal borrows heavily from that prior art, without sticking |
| 39 | +to it in all details. |
| 40 | + |
| 41 | +## 1.2 Inputs to this proposal |
| 42 | +In addition to the references listed above, the discussion at the |
| 43 | +Fortran proposals site |
| 44 | +https://github.com/j3-fortran/fortran_proposals/issues/2 |
| 45 | +influenced this proposal. |
| 46 | + |
| 47 | + |
| 48 | +# 2. Goal |
| 49 | + |
| 50 | +Define a new type, UNSIGNED, with a small set of intrinsic operations |
| 51 | +and intrinsic functions that would satisfy most of the use cases listed |
| 52 | +above. |
| 53 | + |
| 54 | +## 2.1 Value range limitation |
| 55 | + |
| 56 | +An UNSIGNED with n bits has a value range between 0 and 2^n-1. |
| 57 | +(Note that Fortran model integers have values between -2^(n-1)+1 and |
| 58 | +2^(n-1)-1). |
| 59 | + |
| 60 | +## 2.2 Arithmetic is closed over the UNSIGNED value range |
| 61 | + |
| 62 | +All arithmetic operations on UNSIGNED values are closed over |
| 63 | +0 to 2^n-1. Arithmetic operations produce results equal to the |
| 64 | +result of the (mathematical) integers, modulo 2^n. |
| 65 | + |
| 66 | +The following intrinsic binary arithmetic operators are extended |
| 67 | +to support UNSIGNED values: |
| 68 | + + |
| 69 | + - |
| 70 | + * |
| 71 | + / |
| 72 | + |
| 73 | +The unary - operator shall not be applied to. UNSIGNED values. |
| 74 | + |
| 75 | +The exponentiation operator ** shall not be applied to UNSIGNED values. |
| 76 | + |
| 77 | + |
| 78 | +## 2.3 Prohibit mixed-mode arithmetic with INTEGER and REAL |
| 79 | + |
| 80 | +The intrinsic Fortran binary arithmetic operators shall have both |
| 81 | +operands be UNSIGNED if any of the operands is UNSIGNED. |
| 82 | + |
| 83 | +The intrinsic Fortran binary relational operators (defined in R1014 rel-op) |
| 84 | +shall have both operands be UNSIGNED if either of the operands is UNSIGNED. |
| 85 | + |
| 86 | +To perform mixed-mode arithmetic with INTEGER or REAL values, |
| 87 | +the UNSIGNED operand must be converted to an INTEGER or REAL |
| 88 | +value explicitly via the INT or REAL intrinsic functions. |
| 89 | + |
| 90 | + |
| 91 | +# 3. Avoiding traps and pitfalls |
| 92 | + |
| 93 | +There are numerous well-known traps and pitfalls when using unsigned |
| 94 | +integers. We attempt to avoid these as follows: |
| 95 | +- comparison of signed vs. unsigned values: require conversion via |
| 96 | + an intrinsic function or other means. |
| 97 | +- overflow from assignment of large UNSIGNED values to similar-sized |
| 98 | + INTEGER entities: Either accept truncation (modulo 2^(n-1)) or |
| 99 | + specify the KIND with a larger range to the INT intrinsic function. |
| 100 | +- confusion about modulo arithmetic, especially with respect to |
| 101 | + subtraction (e.g., 3u - 5u < 3u .EQV. .false.): Add notes to the |
| 102 | + standard warning about this. |
| 103 | + |
| 104 | + |
| 105 | +# 4. Proposal |
| 106 | + |
| 107 | +- A type name tentatively called UNSIGNED, with the same KIND |
| 108 | + mechanism as for INTEGER, plus a SELECTED_UNSIGNED_KIND function, |
| 109 | + is added to implement unsigned integers. |
| 110 | + |
| 111 | +- Unsigned integer literal constants are marked with a U suffix, |
| 112 | + with an optional KIND specifier attached via the usual underscore. |
| 113 | + |
| 114 | +- Add a conversion function UINT, with an optional KIND. |
| 115 | + |
| 116 | +- Prohibit binary operations between INTEGER and UNSIGNED or |
| 117 | + REAL and UNSIGNED without explicit conversion. |
| 118 | + |
| 119 | +- Permit unsigned integer values in a SELECT CASE. |
| 120 | + |
| 121 | +- Prohibit unsigned integers as index variables in a DO statement |
| 122 | + or as array indices. |
| 123 | + |
| 124 | +- Allow unsigned integers to be read or written in list-directed, |
| 125 | + namelist or unformatted I/O, and by using the usual edit |
| 126 | + descriptors such as I, B, O and Z. |
| 127 | + |
| 128 | +- Allow UNSIGNED arguments to some intrinsics: |
| 129 | + - BGE(UNSIGNED, UNSIGNED) and friends |
| 130 | + - BIT_SIZE(UNSIGNED) |
| 131 | + - BTEST(UNSIGNED, INTEGER) |
| 132 | + - DIGITS(UNSIGNED) |
| 133 | + - DSHIFTL(UNSIGNED, UNSIGNED, INTEGER) |
| 134 | + - DSHIFTR(UNSIGNED, UNSIGNED, INTEGER) |
| 135 | + - HUGE(UNSIGNED) |
| 136 | + - IAND(UNSIGNED, UNSIGNED), IEOR, IOR, NOT |
| 137 | + - IBCLR(UNSIGNED, INTEGER), IBITS, IBSET |
| 138 | + - ISHFT(UNSIGNED, INTEGER, INTEGER) and ISHFTC |
| 139 | + - LEADZ(UNSIGNED) and TRAILZ |
| 140 | + - MERGE_BITS(UNSIGNED, UNSIGNED, UNSIGNED |
| 141 | + - MIN(UNSIGNED, ...) and MAX |
| 142 | + - MOD(UNSIGNED, UNSIGNED) and MODULO |
| 143 | + - MVBITS(UNSIGNED, INTEGER, INTEGER, UNSIGNED, INTEGER) |
| 144 | + - POPCNT(UNSIGNED) and POPPAR |
| 145 | + - RANGE(UNSIGNED) |
| 146 | + - SHIFTA(UNSIGNED, INTEGER), SHIFTL, SHIFTR |
| 147 | + - TRANSFER(UNSIGNED, UNSIGNED, INTEGER) |
| 148 | + |
| 149 | +- Allow UNSIGNED arguments to some array intrinsics: |
| 150 | + - IALL(UNSIGNED array, INTEGER, [, mask]) and friends |
| 151 | + - IPARITY(UNSIGNED array, INTEGER [, mask]) |
| 152 | + - CSHIFT(UNSIGNED array, INTEGER, INTEGER) |
| 153 | + - DOT_PRODUCT(UNSIGNED array, UNSIGNED array) |
| 154 | + - EOSHIFT(UNSIGNED array, INTEGER, INTEGER) |
| 155 | + - FINDLOC(UNSIGNED array, UNSIGNED, ...) |
| 156 | + - MATMUL(UNSIGNED array, UNSIGNED array) |
| 157 | + - MAXLOC(UNSIGNED array, ...), and MINLOC |
| 158 | + - MAXVAL(UNSIGNED array, ...), MINVAL |
| 159 | + |
| 160 | +- Extend ISO_C_BINDING with KIND numbers, for example, |
| 161 | + C_UINT, C_UINT8_T. |
| 162 | + |
| 163 | +- Extend ISO_C_BINDING with other things I forgot to do. |
| 164 | + |
| 165 | +- Extend ISO_Fortran_binding.h appropriately. |
| 166 | + |
| 167 | +- Extend ISO_FORTRAN_ENV with KIND PARAMETERs, for example, |
| 168 | + UINT8, UINT16, UINT32. |
| 169 | + |
| 170 | +- Conversion of an UNSIGNED value to an INTEGER outside the range of |
| 171 | + the integer is processor-dependent. |
| 172 | + |
| 173 | +- Conversion of an INTEGER value to an UNSIGNED outside the range of |
| 174 | + the integer is processor-dependent. |
| 175 | + |
| 176 | +- Conversion of an UNSIGNED value to an INTEGER with a wider range |
| 177 | + is exact. |
| 178 | + |
| 179 | +# 5. Relation to other proposals |
| 180 | + |
| 181 | +This proposal complements the BITS proposal, J3/07-007r2.pdf, as |
| 182 | +proposed in J3/22-195.txt. BITS restricts its operations to logical |
| 183 | +operations and comparisons on bit lengths. This proposal adds arithmetic |
| 184 | +operations. This proposal limits the bit lengths to common powers of two. |
0 commit comments