Home | History | Annotate | Line # | Download | only in lint1
      1  1.56  rillig /*	$NetBSD: msg_132.c,v 1.56 2025/09/14 14:42:52 rillig Exp $	*/
      2   1.1  rillig # 3 "msg_132.c"
      3   1.1  rillig 
      4   1.1  rillig // Test for message: conversion from '%s' to '%s' may lose accuracy [132]
      5   1.1  rillig 
      6   1.3  rillig /*
      7   1.3  rillig  * NetBSD's default lint flags only include a single -a, which only flags
      8   1.3  rillig  * narrowing conversions from long.  To get warnings for all narrowing
      9   1.9  rillig  * conversions, -a needs to be given more than once.
     10   1.3  rillig  *
     11   1.3  rillig  * https://gnats.netbsd.org/14531
     12   1.3  rillig  */
     13   1.3  rillig 
     14  1.51  rillig /* lint1-extra-flags: -aa -X 351 */
     15   1.3  rillig 
     16  1.20  rillig typedef unsigned char u8_t;
     17  1.20  rillig typedef unsigned short u16_t;
     18  1.20  rillig typedef unsigned int u32_t;
     19  1.20  rillig typedef unsigned long long u64_t;
     20  1.20  rillig typedef signed char s8_t;
     21  1.20  rillig typedef signed short s16_t;
     22  1.20  rillig typedef signed int s32_t;
     23  1.20  rillig typedef signed long long s64_t;
     24  1.20  rillig 
     25  1.27  rillig _Bool cond;
     26  1.27  rillig char ch;
     27  1.22  rillig 
     28  1.20  rillig u8_t u8;
     29  1.20  rillig u16_t u16;
     30  1.20  rillig u32_t u32;
     31  1.20  rillig u64_t u64;
     32  1.20  rillig 
     33  1.20  rillig s8_t s8;
     34  1.20  rillig s16_t s16;
     35  1.20  rillig s32_t s32;
     36  1.20  rillig s64_t s64;
     37   1.3  rillig 
     38  1.51  rillig const char *ptr;
     39  1.51  rillig 
     40  1.22  rillig struct bit_fields {
     41  1.22  rillig 	unsigned u1:1;
     42  1.22  rillig 	unsigned u2:2;
     43  1.22  rillig 	unsigned u3:3;
     44  1.22  rillig 	unsigned u4:4;
     45  1.22  rillig 	unsigned u5:5;
     46  1.22  rillig 	unsigned u6:6;
     47  1.22  rillig 	unsigned u7:7;
     48  1.22  rillig 	unsigned u8:8;
     49  1.22  rillig 	unsigned u9:9;
     50  1.22  rillig 	unsigned u10:10;
     51  1.22  rillig 	unsigned u11:11;
     52  1.22  rillig 	unsigned u12:12;
     53  1.22  rillig 	unsigned u32:32;
     54  1.22  rillig } bits;
     55  1.22  rillig 
     56  1.22  rillig 
     57   1.3  rillig void
     58   1.9  rillig unsigned_to_unsigned(void)
     59   1.3  rillig {
     60  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned short' to 'unsigned char' may lose accuracy [132] */
     61  1.18  rillig 	u8 = u16;
     62  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'unsigned char' may lose accuracy [132] */
     63  1.18  rillig 	u8 = u32;
     64  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned char' may lose accuracy [132] */
     65  1.18  rillig 	u8 = u64;
     66   1.9  rillig 
     67   1.9  rillig 	u16 = u8;
     68  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'unsigned short' may lose accuracy [132] */
     69  1.18  rillig 	u16 = u32;
     70  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned short' may lose accuracy [132] */
     71  1.18  rillig 	u16 = u64;
     72   1.9  rillig 
     73   1.9  rillig 	u32 = u8;
     74   1.9  rillig 	u32 = u16;
     75  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned int' may lose accuracy [132] */
     76  1.18  rillig 	u32 = u64;
     77   1.9  rillig 
     78   1.9  rillig 	u64 = u8;
     79   1.9  rillig 	u64 = u16;
     80   1.9  rillig 	u64 = u32;
     81   1.3  rillig }
     82   1.3  rillig 
     83   1.3  rillig void
     84   1.9  rillig unsigned_to_signed(void)
     85   1.3  rillig {
     86  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned short' to 'signed char' may lose accuracy [132] */
     87  1.18  rillig 	s8 = u16;
     88  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'signed char' may lose accuracy [132] */
     89  1.18  rillig 	s8 = u32;
     90  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'signed char' may lose accuracy [132] */
     91  1.18  rillig 	s8 = u64;
     92   1.9  rillig 
     93   1.9  rillig 	s16 = u8;
     94  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'short' may lose accuracy [132] */
     95  1.18  rillig 	s16 = u32;
     96  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'short' may lose accuracy [132] */
     97  1.18  rillig 	s16 = u64;
     98   1.9  rillig 
     99   1.9  rillig 	s32 = u8;
    100   1.9  rillig 	s32 = u16;
    101  1.18  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'int' may lose accuracy [132] */
    102  1.18  rillig 	s32 = u64;
    103   1.9  rillig 
    104   1.9  rillig 	s64 = u8;
    105   1.9  rillig 	s64 = u16;
    106   1.9  rillig 	s64 = u32;
    107   1.9  rillig }
    108   1.9  rillig 
    109   1.9  rillig void
    110   1.9  rillig signed_to_unsigned(void)
    111   1.9  rillig {
    112  1.18  rillig 	/* expect+1: warning: conversion from 'short' to 'unsigned char' may lose accuracy [132] */
    113  1.18  rillig 	u8 = s16;
    114  1.18  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    115  1.18  rillig 	u8 = s32;
    116  1.18  rillig 	/* expect+1: warning: conversion from 'long long' to 'unsigned char' may lose accuracy [132] */
    117  1.18  rillig 	u8 = s64;
    118   1.9  rillig 
    119   1.9  rillig 	u16 = s8;
    120  1.18  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned short' may lose accuracy [132] */
    121  1.18  rillig 	u16 = s32;
    122  1.18  rillig 	/* expect+1: warning: conversion from 'long long' to 'unsigned short' may lose accuracy [132] */
    123  1.18  rillig 	u16 = s64;
    124   1.9  rillig 
    125   1.9  rillig 	u32 = s8;
    126   1.9  rillig 	u32 = s16;
    127  1.18  rillig 	/* expect+1: warning: conversion from 'long long' to 'unsigned int' may lose accuracy [132] */
    128  1.18  rillig 	u32 = s64;
    129   1.9  rillig 
    130   1.9  rillig 	u64 = s8;
    131   1.9  rillig 	u64 = s16;
    132   1.9  rillig 	u64 = s32;
    133   1.9  rillig }
    134   1.9  rillig 
    135   1.9  rillig void
    136   1.9  rillig signed_to_signed(void)
    137   1.9  rillig {
    138  1.18  rillig 	/* expect+1: warning: conversion from 'short' to 'signed char' may lose accuracy [132] */
    139  1.18  rillig 	s8 = s16;
    140  1.18  rillig 	/* expect+1: warning: conversion from 'int' to 'signed char' may lose accuracy [132] */
    141  1.18  rillig 	s8 = s32;
    142  1.18  rillig 	/* expect+1: warning: conversion from 'long long' to 'signed char' may lose accuracy [132] */
    143  1.18  rillig 	s8 = s64;
    144   1.9  rillig 
    145   1.9  rillig 	s16 = s8;
    146  1.18  rillig 	/* expect+1: warning: conversion from 'int' to 'short' may lose accuracy [132] */
    147  1.18  rillig 	s16 = s32;
    148  1.18  rillig 	/* expect+1: warning: conversion from 'long long' to 'short' may lose accuracy [132] */
    149  1.18  rillig 	s16 = s64;
    150   1.9  rillig 
    151   1.9  rillig 	s32 = s8;
    152   1.9  rillig 	s32 = s16;
    153  1.18  rillig 	/* expect+1: warning: conversion from 'long long' to 'int' may lose accuracy [132] */
    154  1.18  rillig 	s32 = s64;
    155   1.9  rillig 
    156   1.9  rillig 	s64 = s8;
    157   1.9  rillig 	s64 = s16;
    158   1.9  rillig 	s64 = s32;
    159   1.3  rillig }
    160   1.4  rillig 
    161   1.5  rillig /*
    162   1.9  rillig  * Before tree.c 1.268 from 2021-04-06, lint wrongly warned that conversion
    163   1.9  rillig  * to _Bool might lose accuracy.  C99 6.3.1.2 defines a special conversion
    164   1.9  rillig  * rule from scalar to _Bool though by comparing the value to 0.
    165   1.5  rillig  */
    166   1.4  rillig _Bool
    167   1.4  rillig to_bool(long a, long b)
    168   1.4  rillig {
    169   1.4  rillig 	/* seen in fp_lib.h, function wideRightShiftWithSticky */
    170   1.5  rillig 	return a | b;
    171   1.4  rillig }
    172   1.6  rillig 
    173   1.6  rillig /* ARGSUSED */
    174   1.6  rillig const char *
    175   1.6  rillig cover_build_plus_minus(const char *arr, double idx)
    176   1.6  rillig {
    177   1.6  rillig 	if (idx > 0.0)
    178  1.33  rillig 		/* expect+2: error: operands of '+' have incompatible types 'pointer to const char' and 'double' [107] */
    179  1.33  rillig 		/* expect+1: error: function 'cover_build_plus_minus' expects to return value [214] */
    180   1.6  rillig 		return arr + idx;
    181   1.6  rillig 	return arr + (unsigned int)idx;
    182   1.6  rillig }
    183   1.7  rillig 
    184   1.7  rillig int
    185   1.7  rillig non_constant_expression(void)
    186   1.7  rillig {
    187   1.7  rillig 	/*
    188   1.7  rillig 	 * Even though this variable definition looks like a constant, it
    189   1.7  rillig 	 * does not fall within C's definition of an integer constant
    190   1.7  rillig 	 * expression.  Due to that, lint does not perform constant folding
    191   1.7  rillig 	 * on the expression built from this variable and thus doesn't know
    192   1.7  rillig 	 * that the conversion will always succeed.
    193   1.7  rillig 	 */
    194   1.7  rillig 	const int not_a_constant = 8;
    195   1.8  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'int' may lose accuracy [132] */
    196   1.8  rillig 	return not_a_constant * 8ULL;
    197   1.7  rillig }
    198  1.10  rillig 
    199  1.10  rillig /*
    200  1.10  rillig  * PR 36668 notices that lint wrongly complains about the possible loss.
    201  1.11  rillig  *
    202  1.11  rillig  * The expression 'u8_t << 8' is guaranteed to fit into an 'u16_t', and its
    203  1.11  rillig  * lower 8 bits are guaranteed to be clear.  'u16_t | u8_t' is guaranteed to
    204  1.11  rillig  * fit into 'u16_t'.
    205  1.11  rillig  *
    206  1.11  rillig  * Since tree.c 1.444 from 2022-05-26, lint tracks simple bitwise and
    207  1.11  rillig  * arithmetic constraints across a single expression.
    208  1.10  rillig  */
    209  1.45  rillig void
    210  1.45  rillig be16dec(void)
    211  1.10  rillig {
    212  1.11  rillig 	/*
    213  1.11  rillig 	 * Before tree.c 1.444 from 2022-05-26, lint complained that the
    214  1.11  rillig 	 * conversion from 'int' to 'unsigned short' may lose accuracy.
    215  1.11  rillig 	 */
    216  1.45  rillig 	u16 = (u16_t)u8 << 8 | u8;
    217  1.10  rillig }
    218  1.10  rillig 
    219  1.10  rillig /*
    220  1.10  rillig  * Since tree.c 1.434 from 2022-04-19, lint infers the possible values of
    221  1.10  rillig  * expressions of the form 'integer & constant', see can_represent.
    222  1.10  rillig  */
    223  1.45  rillig void
    224  1.45  rillig be32enc(void)
    225  1.10  rillig {
    226  1.45  rillig 	u8 = u32 >> 24 & 0xff;
    227  1.45  rillig 	u8 = u32 >> 16 & 0xff;
    228  1.45  rillig 	u8 = u32 >> 8 & 0xff;
    229  1.45  rillig 	u8 = u32 & 0xff;
    230  1.10  rillig }
    231  1.12  rillig 
    232  1.43  rillig void
    233  1.43  rillig test_ic_mult(void)
    234  1.43  rillig {
    235  1.45  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    236  1.45  rillig 	u8 = u8 * u8;
    237  1.45  rillig 	u16 = u8 * u8;
    238  1.45  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned short' may lose accuracy [132] */
    239  1.45  rillig 	u16 = u16 * u8;
    240  1.45  rillig 	u32 = u16 * u16;
    241  1.45  rillig 
    242  1.44  rillig 	u32 = u16 * 65537ULL;
    243  1.43  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned int' may lose accuracy [132] */
    244  1.44  rillig 	u32 = u16 * 65538ULL;
    245  1.43  rillig 
    246  1.43  rillig 	u16 = 0 * u16;
    247  1.43  rillig 	u16 = 1 * u16;
    248  1.43  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned short' may lose accuracy [132] */
    249  1.43  rillig 	u16 = 2 * u16;
    250  1.43  rillig 
    251  1.45  rillig 	// from __BITS, __SHIFTIN, __SHIFTOUT
    252  1.43  rillig 	u32 = (u16 & 1023ULL) / 1ULL * 1024ULL | (u16 & 1023ULL) / 1ULL * 1ULL;
    253  1.50  rillig 
    254  1.50  rillig 	s8 = 1 * s8;
    255  1.50  rillig 	s16 = 1 * s16;
    256  1.50  rillig 	s32 = 1 * s32;
    257  1.50  rillig 	s64 = 1 * s64;
    258  1.52  rillig 
    259  1.52  rillig 	/* expect+1: warning: conversion from 'int' to 'signed char' may lose accuracy [132] */
    260  1.52  rillig 	s8 = 2 * s8;
    261  1.52  rillig 	/* expect+1: warning: conversion from 'int' to 'short' may lose accuracy [132] */
    262  1.52  rillig 	s16 = 2 * s16;
    263  1.52  rillig 	// No warning, as there is no narrowing conversion.
    264  1.52  rillig 	s32 = 2 * s32;
    265  1.52  rillig 	// No warning, as there is no narrowing conversion.
    266  1.52  rillig 	s64 = 2 * s64;
    267  1.52  rillig 
    268  1.52  rillig 	/* expect+1: warning: conversion from 'int' to 'signed char' may lose accuracy [132] */
    269  1.52  rillig 	s8 = -1 * s8;
    270  1.52  rillig 	/* expect+1: warning: conversion from 'int' to 'short' may lose accuracy [132] */
    271  1.52  rillig 	s16 = -1 * s16;
    272  1.52  rillig 	// No warning, as there is no narrowing conversion.
    273  1.52  rillig 	s32 = -1 * s32;
    274  1.52  rillig 	// No warning, as there is no narrowing conversion.
    275  1.52  rillig 	s64 = -1 * s64;
    276  1.43  rillig }
    277  1.43  rillig 
    278  1.45  rillig void
    279  1.45  rillig test_ic_div(void)
    280  1.12  rillig {
    281  1.45  rillig 	u8 = u8 / u8;
    282  1.45  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    283  1.45  rillig 	u8 = u16 / u8;
    284  1.45  rillig 	u16 = u8 / u8;
    285  1.45  rillig 	u16 = u32 / 65536;
    286  1.45  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'unsigned short' may lose accuracy [132] */
    287  1.45  rillig 	u16 = u32 / 65535;
    288  1.50  rillig 
    289  1.50  rillig 	s8 = s8 / 1;
    290  1.50  rillig 	s16 = s16 / 1;
    291  1.50  rillig 	s32 = s32 / 1;
    292  1.50  rillig 	s64 = s64 / 1;
    293  1.52  rillig 
    294  1.52  rillig 	/* expect+1: warning: conversion from 'int' to 'signed char' may lose accuracy [132] */
    295  1.52  rillig 	s8 = s8 / -1;
    296  1.52  rillig 	/* expect+1: warning: conversion from 'int' to 'short' may lose accuracy [132] */
    297  1.52  rillig 	s16 = s16 / -1;
    298  1.52  rillig 	// No warning, as there is no narrowing conversion.
    299  1.52  rillig 	s32 = s32 / -1;
    300  1.52  rillig 	// No warning, as there is no narrowing conversion.
    301  1.52  rillig 	s64 = s64 / -1;
    302  1.20  rillig }
    303  1.22  rillig 
    304  1.22  rillig void
    305  1.22  rillig test_ic_mod(void)
    306  1.22  rillig {
    307  1.22  rillig 	/* The result is between 0 and 254. */
    308  1.23  rillig 	u8 = u64 % u8;
    309  1.23  rillig 
    310  1.23  rillig 	/* The result is between 0 and 255. */
    311  1.23  rillig 	u8 = u64 % 256;
    312  1.23  rillig 
    313  1.23  rillig 	/* The result is between 0 and 256. */
    314  1.22  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned char' may lose accuracy [132] */
    315  1.23  rillig 	u8 = u64 % 257;
    316  1.22  rillig 
    317  1.22  rillig 	/* The result is between 0 and 1000. */
    318  1.22  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned char' may lose accuracy [132] */
    319  1.22  rillig 	u8 = u64 % 1000;
    320  1.22  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned int:9' may lose accuracy [132] */
    321  1.22  rillig 	bits.u9 = u64 % 1000;
    322  1.22  rillig 	bits.u10 = u64 % 1000;
    323  1.23  rillig 	u16 = u64 % 1000;
    324  1.22  rillig 
    325  1.46  rillig 	s8 = s16 % s8;
    326  1.23  rillig 	/* expect+1: warning: conversion from 'int' to 'signed char' may lose accuracy [132] */
    327  1.46  rillig 	s8 = s16 % s16;
    328  1.46  rillig 	s8 = s64 % 1;
    329  1.46  rillig 	s8 = s64 % (s16 & 1);
    330  1.46  rillig 	/* expect+1: warning: conversion from 'long long' to 'signed char' may lose accuracy [132] */
    331  1.46  rillig 	s8 = s64 % (s16 & 0);
    332  1.46  rillig 	s8 = (s64 & 0x7f) % s64;
    333  1.23  rillig 	/* expect+1: warning: conversion from 'long long' to 'signed char' may lose accuracy [132] */
    334  1.46  rillig 	s8 = (s64 & 0xff) % s64;
    335  1.22  rillig }
    336  1.24  rillig 
    337  1.24  rillig void
    338  1.47  rillig test_ic_plus(void)
    339  1.47  rillig {
    340  1.47  rillig 	/* expect+1: warning: conversion from 'long long' to 'signed char' may lose accuracy [132] */
    341  1.47  rillig 	s8 = -129 + s64 % 1;
    342  1.47  rillig 	s8 = -128 + s64 % 1;
    343  1.47  rillig 	s8 = 127 + s64 % 1;
    344  1.47  rillig 	/* expect+1: warning: conversion from 'long long' to 'signed char' may lose accuracy [132] */
    345  1.47  rillig 	s8 = 128 + s64 % 1;
    346  1.47  rillig 
    347  1.47  rillig 	/* expect+2: warning: conversion of negative constant -129 to unsigned type 'unsigned long long' [222] */
    348  1.47  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'signed char' may lose accuracy [132] */
    349  1.47  rillig 	s8 = -129 + u64 % 1;
    350  1.47  rillig 	/* expect+2: warning: conversion of negative constant -128 to unsigned type 'unsigned long long' [222] */
    351  1.47  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'signed char' may lose accuracy [132] */
    352  1.47  rillig 	s8 = -128 + u64 % 1;
    353  1.47  rillig 	s8 = 127 + u64 % 1;
    354  1.47  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'signed char' may lose accuracy [132] */
    355  1.47  rillig 	s8 = 128 + u64 % 1;
    356  1.47  rillig 
    357  1.47  rillig 	u8 = 0 + u64 % 1;
    358  1.47  rillig 	u8 = 255 + u64 % 1;
    359  1.47  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned char' may lose accuracy [132] */
    360  1.47  rillig 	u8 = 256 + u64 % 1;
    361  1.47  rillig 
    362  1.50  rillig 	u8 = s8 + 0x80;
    363  1.50  rillig 	u16 = s16 + 0x8000;
    364  1.50  rillig 	u32 = s32 + 0x80000000;
    365  1.50  rillig 	u64 = s64 + 0x8000000000000000;
    366  1.50  rillig 
    367  1.49  rillig 	// XXX: No warnings since portable_rank_cmp is the same for both sides.
    368  1.49  rillig 	bits.u11 = bits.u10 + bits.u10 + 1;
    369  1.49  rillig 	bits.u11 = bits.u10 + bits.u10 + 2;
    370  1.49  rillig 	bits.u11 = bits.u10 + 1024;
    371  1.49  rillig 	bits.u11 = bits.u10 + 1025;
    372  1.49  rillig 
    373  1.49  rillig 	u8 = bits.u7 + bits.u7 + 1;
    374  1.49  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    375  1.49  rillig 	u8 = bits.u7 + bits.u7 + 2;
    376  1.49  rillig 	u8 = bits.u7 + 128;
    377  1.49  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    378  1.49  rillig 	u8 = bits.u7 + 129;
    379  1.49  rillig 
    380  1.49  rillig 	// The result of the second '+' wraps around, thus the warning,
    381  1.49  rillig 	// even though the final result fits in a u16.
    382  1.49  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'unsigned short' may lose accuracy [132] */
    383  1.49  rillig 	u16 = u32 % 0x00010000 + 0x80000000 + 0x80000000;
    384  1.49  rillig 
    385  1.49  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'unsigned short' may lose accuracy [132] */
    386  1.49  rillig 	u16 = u32 % 0x00010000 + 0xffff8000;
    387  1.49  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'short' may lose accuracy [132] */
    388  1.49  rillig 	s16 = u32 % 0x00010000 + 0xffff8000;
    389  1.49  rillig 
    390  1.49  rillig 	/* expect+1: warning: conversion from 'long long' to 'unsigned short' may lose accuracy [132] */
    391  1.49  rillig 	u16 = s64 % 0x00010000 + 0xffffffffLL + -0xffffffffLL;
    392  1.49  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned short' may lose accuracy [132] */
    393  1.49  rillig 	u16 = s32 % 0x00010000 + 0x7fff0000 + -0x7fff0000;
    394  1.49  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'unsigned short' may lose accuracy [132] */
    395  1.49  rillig 	u16 = u32 % 0x00010000 + 0xffff0000 + 0x00010000;
    396  1.49  rillig 
    397  1.47  rillig 	s8 = '0' + s64 % 10;
    398  1.51  rillig 
    399  1.51  rillig 	ptr = ptr + 3;
    400  1.47  rillig }
    401  1.47  rillig 
    402  1.47  rillig void
    403  1.49  rillig test_ic_minus(void)
    404  1.49  rillig {
    405  1.49  rillig 	// Shift the range [0x00 to 0xff] to [-0x80 to 0x7f].
    406  1.49  rillig 	s8 = (s64 & 0xff) - 0x80;
    407  1.49  rillig 
    408  1.49  rillig 	// Sign-extend the lowest bits.
    409  1.49  rillig 	s8 = ((s64 & 0xff) ^ 0x80) - 0x80;
    410  1.49  rillig 	s16 = ((s64 & 0xffff) ^ 0x8000) - 0x8000;
    411  1.54  rillig 	/* expect+1: warning: '&' converts 'unsigned int' with its most significant bit being set to 'long long' [309] */
    412  1.49  rillig 	s32 = ((s64 & 0xffffffff) ^ 0x80000000) - 0x80000000;
    413  1.49  rillig 
    414  1.49  rillig 	// Trying to sign-extend, but with off-by-one errors.
    415  1.49  rillig 	/* expect+1: warning: conversion from 'long long' to 'signed char' may lose accuracy [132] */
    416  1.49  rillig 	s8 = ((s64 & 0xff) ^ 0x80) - 0x7f;
    417  1.49  rillig 	/* expect+1: warning: conversion from 'long long' to 'signed char' may lose accuracy [132] */
    418  1.49  rillig 	s8 = ((s64 & 0xff) ^ 0x80) - 0x81;
    419  1.50  rillig 
    420  1.50  rillig 	u8 = s8 - -0x80;
    421  1.50  rillig 	u16 = s16 - -0x8000;
    422  1.50  rillig 	u32 = s32 - -0x80000000;
    423  1.50  rillig 	u64 = s64 - -0x8000000000000000;
    424  1.51  rillig 
    425  1.51  rillig 	ptr = ptr - 3;
    426  1.51  rillig 	s64 = ptr + 3 - ptr;
    427  1.49  rillig }
    428  1.49  rillig 
    429  1.49  rillig void
    430  1.45  rillig test_ic_shl(void)
    431  1.45  rillig {
    432  1.45  rillig 	u64 = u64 << u64;
    433  1.45  rillig 	s64 = s64 << s64;
    434  1.45  rillig 
    435  1.45  rillig 	u16 = u8 << 8;
    436  1.45  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned short' may lose accuracy [132] */
    437  1.45  rillig 	u16 = u8 << 9;
    438  1.56  rillig 	/* expect+1: warning: bitwise '<<' on signed 'int promoted from unsigned short' possibly nonportable [117] */
    439  1.45  rillig 	u32 = u16 << 16;
    440  1.45  rillig 	// XXX: missing warning as UINT has the same rank as INT, see portable_rank_cmp.
    441  1.45  rillig 	u32 = u16 << 17;
    442  1.55  rillig 	/* expect+1: warning: shift amount 56 is greater than bit-size 32 of 'int promoted from unsigned char' [122] */
    443  1.45  rillig 	u64 = u8 << 56;
    444  1.45  rillig 	u64 = (u64_t)u8 << 56;
    445  1.45  rillig 	// XXX: missing warning, as the operand types of '=' are the same, thus no conversion.
    446  1.45  rillig 	u64 = (u64_t)u8 << 57;
    447  1.55  rillig 	/* expect+1: warning: shift amount 48 is greater than bit-size 32 of 'int promoted from unsigned short' [122] */
    448  1.45  rillig 	u64 = u16 << 48;
    449  1.45  rillig 	u64 = (u64_t)u16 << 48;
    450  1.45  rillig 	// XXX: missing warning, as the operand types of '=' are the same, thus no conversion.
    451  1.45  rillig 	u64 = (u64_t)u16 << 49;
    452  1.45  rillig 	/* expect+1: warning: shift amount 32 equals bit-size of 'unsigned int' [267] */
    453  1.45  rillig 	u64 = u32 << 32;
    454  1.45  rillig 	u64 = (u64_t)u32 << 32;
    455  1.45  rillig 	// XXX: missing warning, as the operand types of '=' are the same, thus no conversion.
    456  1.45  rillig 	u64 = (u64_t)u32 << 33;
    457  1.45  rillig }
    458  1.45  rillig 
    459  1.45  rillig void
    460  1.45  rillig test_ic_shr(void)
    461  1.24  rillig {
    462  1.45  rillig 	u64 = u64 >> u64;
    463  1.45  rillig 	s64 = s64 >> s64;
    464  1.45  rillig 
    465  1.45  rillig 	u32 = u64 >> 32;
    466  1.45  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned int' may lose accuracy [132] */
    467  1.45  rillig 	u32 = u64 >> 31;
    468  1.45  rillig 	u16 = u64 >> 48;
    469  1.45  rillig 	u16 = u32 >> 16;
    470  1.45  rillig 	u8 = u64 >> 56;
    471  1.45  rillig 	u8 = u32 >> 24;
    472  1.45  rillig 	u8 = u16 >> 8;
    473  1.45  rillig 
    474  1.24  rillig 	/*
    475  1.45  rillig 	 * No matter whether the big integer is signed or unsigned, the
    476  1.45  rillig 	 * result of '&' is guaranteed to be an unsigned value.
    477  1.24  rillig 	 */
    478  1.45  rillig 	u8 = (s64 & 0xf0) >> 4;
    479  1.45  rillig 	u8 = (s8 & 0xf0) >> 4;
    480  1.45  rillig }
    481  1.24  rillig 
    482  1.45  rillig void
    483  1.45  rillig test_ic_bitand(void)
    484  1.45  rillig {
    485  1.24  rillig 	u8 = u8 & u16;
    486  1.24  rillig 
    487  1.24  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'unsigned char' may lose accuracy [132] */
    488  1.24  rillig 	u8 = u16 & u32;
    489  1.24  rillig }
    490  1.27  rillig 
    491  1.27  rillig void
    492  1.49  rillig test_ic_bitxor(void)
    493  1.49  rillig {
    494  1.49  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    495  1.49  rillig 	u8 = u8 ^ u16;
    496  1.49  rillig 	u16 = u8 ^ u16;
    497  1.49  rillig 
    498  1.49  rillig 	// Sign-extend.
    499  1.49  rillig 	s8 = (u8 ^ 0x80) - 0x80;
    500  1.49  rillig 	s16 = (u16 ^ 0x8000) - 0x8000;
    501  1.49  rillig 	s32 = (u32 ^ 0x80000000) - 0x80000000;
    502  1.49  rillig 	s64 = (u64 ^ 0x8000000000000000) - 0x8000000000000000;
    503  1.49  rillig }
    504  1.49  rillig 
    505  1.49  rillig void
    506  1.45  rillig test_ic_bitor(void)
    507  1.28  rillig {
    508  1.45  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    509  1.45  rillig 	u8 = u8 | u16;
    510  1.45  rillig 	u16 = u8 | u16;
    511  1.45  rillig 	/* expect+1: warning: conversion from 'unsigned int' to 'unsigned short' may lose accuracy [132] */
    512  1.45  rillig 	u16 = u8 | u32;
    513  1.45  rillig 	u32 = u8 | u32;
    514  1.45  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned int' may lose accuracy [132] */
    515  1.45  rillig 	u32 = u8 | u64;
    516  1.45  rillig 	u64 = u8 | u64;
    517  1.28  rillig }
    518  1.28  rillig 
    519  1.28  rillig void
    520  1.45  rillig test_ic_quest_colon(char c1, char c2)
    521  1.27  rillig {
    522  1.27  rillig 	/* Both operands are representable as char. */
    523  1.27  rillig 	ch = cond ? '?' : ':';
    524  1.27  rillig 
    525  1.27  rillig 	/*
    526  1.27  rillig 	 * Both operands are representable as char. Clang-Tidy 17 wrongly
    527  1.27  rillig 	 * warns about a narrowing conversion from 'int' to signed type
    528  1.27  rillig 	 * 'char'.
    529  1.27  rillig 	 */
    530  1.27  rillig 	ch = cond ? c1 : c2;
    531  1.27  rillig 
    532  1.30  rillig 	/*
    533  1.45  rillig 	 * Mixing s8 and u8 results in a number from -128 to 255, which neither
    534  1.45  rillig 	 * fits in s8 nor u8.
    535  1.30  rillig 	 */
    536  1.27  rillig 	/* expect+1: warning: conversion from 'int' to 'signed char' may lose accuracy [132] */
    537  1.27  rillig 	s8 = cond ? s8 : u8;
    538  1.27  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    539  1.27  rillig 	u8 = cond ? s8 : u8;
    540  1.27  rillig }
    541  1.34  rillig 
    542  1.34  rillig void
    543  1.45  rillig test_ic_con(void)
    544  1.45  rillig {
    545  1.45  rillig 	/* expect+1: warning: assignment of negative constant -1 to unsigned type 'unsigned char' [164] */
    546  1.45  rillig 	u8 = -1;
    547  1.45  rillig 	u8 = 0;
    548  1.45  rillig 	u8 = 255;
    549  1.45  rillig 	/* expect+1: warning: constant truncated by assignment [165] */
    550  1.45  rillig 	u8 = 256;
    551  1.45  rillig 
    552  1.45  rillig 	/* expect+1: warning: conversion of 'int' to 'signed char' is out of range [119] */
    553  1.45  rillig 	s8 = -129;
    554  1.45  rillig 	s8 = -128;
    555  1.45  rillig 	s8 = 127;
    556  1.45  rillig 	/* expect+1: warning: conversion of 'int' to 'signed char' is out of range [119] */
    557  1.45  rillig 	s8 = 128;
    558  1.45  rillig }
    559  1.45  rillig 
    560  1.45  rillig void
    561  1.45  rillig test_ic_cvt(void)
    562  1.45  rillig {
    563  1.45  rillig 	u16 = (u32 & 0x0000ff00);
    564  1.45  rillig 	u16 = (u32_t)(u32 & 0x0000ff00);
    565  1.45  rillig 	u16 = (u16_t)u32;
    566  1.45  rillig 	u16 = (u8_t)(u32 & 0xffff) << 8;
    567  1.50  rillig 	u16 = (int)3.0;
    568  1.50  rillig 
    569  1.50  rillig 	u8 = (u8_t)(u64 & 0x0f);
    570  1.50  rillig 	u8 = (u8_t)(u64 & 0x0f) << 4;
    571  1.50  rillig 	/* expect+1: warning: conversion from 'int' to 'unsigned char' may lose accuracy [132] */
    572  1.50  rillig 	u8 = (u8_t)(u64 & 0x0f) << 5;
    573  1.45  rillig }
    574  1.45  rillig 
    575  1.45  rillig unsigned char
    576  1.45  rillig test_bit_fields(unsigned long long m)
    577  1.45  rillig {
    578  1.45  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned int:3' may lose accuracy [132] */
    579  1.45  rillig 	bits.u3 = bits.u32 & m;
    580  1.45  rillig 
    581  1.45  rillig 	bits.u5 = bits.u3 & m;
    582  1.45  rillig 	bits.u32 = bits.u5 & m;
    583  1.45  rillig 
    584  1.45  rillig 	/* expect+1: warning: conversion from 'unsigned long long' to 'unsigned char' may lose accuracy [132] */
    585  1.45  rillig 	return bits.u32 & m;
    586  1.45  rillig }
    587  1.45  rillig 
    588  1.45  rillig void
    589  1.36  rillig compare_bit_field_to_integer_constant(void)
    590  1.34  rillig {
    591  1.36  rillig 	static _Bool b;
    592  1.36  rillig 	static struct {
    593  1.36  rillig 		short s16:15;
    594  1.36  rillig 		unsigned short u16:15;
    595  1.36  rillig 		int s32:15;
    596  1.36  rillig 		unsigned u32:15;
    597  1.36  rillig 		long long s64:15;
    598  1.36  rillig 		unsigned long long u64:15;
    599  1.36  rillig 	} s;
    600  1.34  rillig 
    601  1.35  rillig 	// Since decl.c 1.180 from 2021-05-02 and before tree.c 1.624 from
    602  1.35  rillig 	// 2024-03-12, lint warned about a possible loss of accuracy [132]
    603  1.36  rillig 	// when promoting an 'unsigned long long' bit-field to 'int'.
    604  1.36  rillig 	b = s.s16 == 0;
    605  1.36  rillig 	b = s.u16 == 0;
    606  1.36  rillig 	b = s.s32 == 0;
    607  1.36  rillig 	b = s.u32 == 0;
    608  1.36  rillig 	b = s.s64 == 0;
    609  1.36  rillig 	b = s.u64 == 0;
    610  1.36  rillig 	b = !b;
    611  1.34  rillig }
    612  1.37  rillig 
    613  1.38  rillig /*
    614  1.38  rillig  * Before tree.c 1.626 from 2024-03-26, the usual arithmetic conversions for
    615  1.38  rillig  * bit-field types with the same base type but different widths simply took
    616  1.38  rillig  * the type of the left operand, leading to wrong warnings about loss of
    617  1.38  rillig  * accuracy when the right operand was wider than the left operand.
    618  1.38  rillig  */
    619  1.38  rillig void
    620  1.37  rillig binary_operators_on_bit_fields(void)
    621  1.37  rillig {
    622  1.37  rillig 	struct {
    623  1.38  rillig 		u64_t u15:15;
    624  1.38  rillig 		u64_t u48:48;
    625  1.38  rillig 		u64_t u64;
    626  1.37  rillig 	} s = { 0, 0, 0 };
    627  1.37  rillig 
    628  1.37  rillig 	u64 = s.u15 | s.u48;
    629  1.38  rillig 	u64 = s.u48 | s.u15;
    630  1.37  rillig 	u64 = s.u15 | s.u48 | s.u64;
    631  1.38  rillig 	u64 = s.u64 | s.u48 | s.u15;
    632  1.38  rillig 	cond = (s.u15 | s.u48 | s.u64) != 0;
    633  1.38  rillig 	cond = (s.u64 | s.u48 | s.u15) != 0;
    634  1.39  rillig 
    635  1.40  rillig 	// Before tree.c from 1.638 from 2024-05-01, lint wrongly warned:
    636  1.40  rillig 	// warning: conversion of 'int' to 'int:4' is out of range [119]
    637  1.39  rillig 	s32 = 8 - bits.u3;
    638  1.37  rillig }
    639  1.41  rillig 
    640  1.41  rillig unsigned char
    641  1.43  rillig combine_arithmetic_and_bit_operations(void)
    642  1.41  rillig {
    643  1.43  rillig 	return 0xc0 | (u32 & 0x07c0) / 64;
    644  1.41  rillig }
    645