<table border="1" cellspacing="0" cellpadding="8">
    <tr>
        <th>Issue</th>
        <td>
            <a href=http://email.email.llvm.org/c/eJztWUtz4jgQ_jXm0gWFH4A5cEhIspVDducwVVNzSglZxtrYkleSk7C_fluywIT3bkjVHoZygUW3PvXL8tf2Qmar2Y-CCVCNEFwsIRgP-z8o0ab_V0NKHAHRUBNlQOatkL0ytTIFKltpEKWP8CLkWxDNgZsgmmgQ0oBiVFYVExnLgvgWHqHkL8wpzIGIDP8wjRIImoOuGeU5p_BGlLVBB9HUqs1LggZxQaVCNFOunIIGspCNAWujNZhYq6gU2ljrrNGIxTKoJReGKTASVYQU_ZNqzvoc7QOuYcEssF2gnW1WNQNTECfE6XacsRzP0F3EcEqb9VA4CIZ3wfCm_X7iglekBPZOqrpkQXyzLbUg7dEOoxgdLpuMQRDPtckQdFAE8f32HL8-NELzpUADaEHQgxuoVs-1USEG_IiiLqQynWZ0XBPX7fSS43qlxDrYKKYbxROWWl2EP2emVztto1c6Y6DX2rUOg42qXDB4-vn8dP80__bz-fH3OZa0wBKEYDT3epPbbgD4QYdRCY_WaxzHeICblbmp8V2n5KoODqi6Qo93sDNUubXzxZ5IHxYFk7v25FXyzK7qBtWqYhWtV2iA_x-vSW0UpwYyPLEV31q2J9aKWqnmf7Nn40zdCdwXLrQO-Hq56V6Rd-AuzG6Jzrxpu9TxWdrNsivvFMNwuvFg6iK8I92tkbAzd18YnRImp4TplnBj14dyC8-XWbhVXsdgovMw0QUwyXmY5AKY9DxMegBmF2w376dQD-ketXJvC70IeVv5PHS7514E3Kmeh_Vb9EW4W7pnIr3exE8Df9Q6VQNuq78ELLoMLLkILLkMLL0ILD0ZOcUc48k6yXrf3uUA_ubkiRUyD6QdVCIlwN8NHYJcqpb8bLZfuyyC4L3BFAyk4ksukHi4qW9I4w5pA8WUs46VKZY11BaY0W5fHuxsR485rGQDmrwytwqSMTzz3MZyRcuPcK8dUEeP5ghJSi2hsBOcAU_kBW-6SIRwcesDRvCVCc4EPcONjNvpu4BSxw-RkCqFMNvEFAdC9h2LRZ63FNCX4IyS0KfgzdtaiJaMiG1oVUFf5X7OiST90Zi6WVNjb08fzdBcCpeKU_60-l4bwngwHISt5DtRS2Z9hfd0_DxO-jXtl1w07_2laLxKoRjJoMLcllaxlpq_-xRhRZKyZNkdV1YURA-Nxg3uoeQL-12-VvgTIg95WHBxwrtHR3htllsqXhP6QpZYHIsV_MaEkXJwoDSwk3B1hmn2JeCqsY0U4mGN5LIs5Zu-JDyfS68_j29im4vIRsPB2RPH73MlKwzQ5MAdob3GJ5bd489BUaZkrT25WbcUKBzdeqvR-e1manTXcTn7Oc4o1hrB6H7HkXCEX4n9sm0Wcx6918T2Wa0zFaHKWbyDPtlB_kIK-y8_-07G4bWy1XYSX5Ou6Fe6fLqia6XLdnRfk6zkV7J8suJrJct11l-TrfRXtny2rH_x5H9247pGQ_q5sIyvFpZr3iGu0WF_Li6Tq8XlelvxNR4YfC4q6dWicsU97xoPQP5LWNI2CBqWTDBFDMs8i3eM3fULN-1hfdl0a_6m4Zqw0R3cO1YenugebrRrBygRoBlb9wH-GT9IUa7AYIu6xP4H3uwriEb7FxCtt8HkFneNOV4hc6yHeWrbZWwZ7QNebdHsWwaLuCCabf-r3L8tjH1McgJmAGikbmjRNqoLVnLm-9pFs2zbbTdyj_YJNbZRWzDzxpj44I3tnf2qH14OtC8o2vcHey8JoJfN4mwaT0mPNAa3odmSvHJRSETNeo0qZ4UxteuSogc8ltwUzWJAZdV1cfanXyv5J6MGh1zrxsbhYRSn6bhXzPJxEo6GQ7pIMpbk0TCfpCMSjhd5QrOERqNeSdBrPcNMB1Ek2Bs4CDzHJPc-bwGfRcMIj3AcTkbDeDQYTfKQxeF0nCfjcZxEQTJkFeHlwOIMpFr21MxBYgI0Ckuuje6ERLsLkTmD0ULDTclmc98qbi42eNx6a_R9XWWYPALf_QuCbz4VdtxzVs-cyf8AIb2kSg>53886</a>
        </td>
    </tr>

    <tr>
        <th>Summary</th>
        <td>
            Clang -Wcast-qual Incorrectly Triggers on a Typedef Pointer Type
        </td>
    </tr>

    <tr>
      <th>Labels</th>
      <td>
            new issue
      </td>
    </tr>

    <tr>
      <th>Assignees</th>
      <td>
      </td>
    </tr>

    <tr>
      <th>Reporter</th>
      <td>
          gavinhoward
      </td>
    </tr>
</table>

<pre>
    When running `-Wcast-qual` as part of `-Weverything` (I know, it's not recommended; I like it, and I turn off specific warnings), Clang incorrectly warns about casting a `const`-qualified pointer to a non-`const`-qualified pointer, if it is being cast to a type that is `typedef`'ed to a pointer type.

Minimal example:

```
#include <stdint.h>

typedef unsigned char* my_ptr1;
typedef unsigned short* my_ptr2;
typedef unsigned int* my_ptr4;
typedef unsigned long* my_ptr8;

typedef unsigned char my_int1;
typedef unsigned short my_int2;
typedef unsigned int my_int4;
typedef unsigned long my_int8;

#define MY_MEMCPY_INC(n) \
{ \
    *((my_ptr ## n) d) = *((const my_ptr ## n) s); \
    d += n; \
    s += n; \
}
void*
mymemcpy(void* restrict dest, const void* restrict src, size_t n);

void*
mymemcpy(void* restrict dest, const void* restrict src, size_t n)
{
        unsigned char* restrict d = dest;
        const unsigned char* restrict s = src;

        (void) n;

        MY_MEMCPY_INC(1)
        MY_MEMCPY_INC(2)
        MY_MEMCPY_INC(4)
        MY_MEMCPY_INC(8)

        *((my_ptr1) d) = *((const my_ptr1) s);
        *((my_ptr2) d) = *((const my_ptr2) s);
        *((my_ptr4) d) = *((const my_ptr4) s);
        *((my_ptr8) d) = *((const my_ptr8) s);

        *((unsigned char*) d) = *((const unsigned char*) s);
        *((unsigned short*) d) = *((const unsigned short*) s);
        *((unsigned int*) d) = *((const unsigned int*) s);
        *((unsigned long*) d) = *((const unsigned long*) s);

        *((my_int1*) d) = *((const my_int1*) s);
        *((my_int2*) d) = *((const my_int2*) s);
        *((my_int4*) d) = *((const my_int4*) s);
        *((my_int8*) d) = *((const my_int8*) s);

        return d;
}
```

(I know this code is incorrect for a `memcpy()`; the original code was a `memcpy()` clone, and I reduced its size.)

If you save the above example as `test.c`, I also have a `Makefile` for convenience:

```
test:
        clang -Werror -Weverything -Wno-cast-align -o test.o -c test.c

clean:
        rm -rf test.o
```

Output of `clang --version`:

```
clang version 13.0.1
Target: x86_64-pc-linux-gnu
Thread model: posix
InstalledDir: /usr/lib/llvm/13/bin
```

It is the Clang packaged by Gentoo.

If you run `make`, the output is as follows:

```
clang -Werror -Weverything -Wno-cast-align -o test.o -c test.c
test.c:30:2: error: cast from 'const unsigned char *' to 'unsigned char *' drops const qualifier [-Werror,-Wcast-qual]
        MY_MEMCPY_INC(1)
        ^
test.c:15:45: note: expanded from macro 'MY_MEMCPY_INC'
        *((my_ptr ## n) d) = *((const my_ptr ## n) s); \
                                                   ^
test.c:31:2: error: cast from 'const unsigned char *' to 'unsigned short *' drops const qualifier [-Werror,-Wcast-qual]
        MY_MEMCPY_INC(2)
        ^
test.c:15:45: note: expanded from macro 'MY_MEMCPY_INC'
        *((my_ptr ## n) d) = *((const my_ptr ## n) s); \
                                                   ^
test.c:32:2: error: cast from 'const unsigned char *' to 'unsigned int *' drops const qualifier [-Werror,-Wcast-qual]
        MY_MEMCPY_INC(4)
        ^
test.c:15:45: note: expanded from macro 'MY_MEMCPY_INC'
        *((my_ptr ## n) d) = *((const my_ptr ## n) s); \
                                                   ^
test.c:33:2: error: cast from 'const unsigned char *' to 'unsigned long *' drops const qualifier [-Werror,-Wcast-qual]
        MY_MEMCPY_INC(8)
        ^
test.c:15:45: note: expanded from macro 'MY_MEMCPY_INC'
        *((my_ptr ## n) d) = *((const my_ptr ## n) s); \
                                                   ^
test.c:35:37: error: cast from 'const unsigned char *' to 'unsigned char *' drops const qualifier [-Werror,-Wcast-qual]
        *((my_ptr1) d) = *((const my_ptr1) s);
                                           ^
test.c:36:37: error: cast from 'const unsigned char *' to 'unsigned short *' drops const qualifier [-Werror,-Wcast-qual]
        *((my_ptr2) d) = *((const my_ptr2) s);
                                           ^
test.c:37:37: error: cast from 'const unsigned char *' to 'unsigned int *' drops const qualifier [-Werror,-Wcast-qual]
        *((my_ptr4) d) = *((const my_ptr4) s);
                                           ^
test.c:38:37: error: cast from 'const unsigned char *' to 'unsigned long *' drops const qualifier [-Werror,-Wcast-qual]
        *((my_ptr8) d) = *((const my_ptr8) s);
                                           ^
8 errors generated.
make: *** [Makefile:2: test] Error 1
```

As you can see, the warning only triggers when using `my_ptr{1,2,4,8}` types, not the base types, nor the `my_int{1,2,4,8}` types. As such, I believe the bug is in the interaction between the warning and the `typedef`'ing a type to a pointer type. 
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJztWU1v8jgQ_jXhMgKRBEg4cGhpu-qhu--h0qv3VJnEId4mdtZ2Stlfv2PHEMpHYLdU2kNRBDEzfjxfcZ5JFiJdz37mlIOsOWd8Cd5k2P-ZEKX7f9WkwBEQBRWRGkTWCOkblWudo7KRekH8CK9crLxgDkx7QaSACw2SJqIsKU9p6oW38AgFe6VWYQ6Ep_iHriVH0AxURROWsQRWRBoblBdMjdq8IGgQ44mQiKaLtVVQQBai1mBsNAYTY1UiuNLGOmM0YtEUKsG4phK0QBUueL9TzVqfoX3AFCyoATYLNLP1uqKgc2KFON2MU5rhGbqLGFZpux4KB97wzhveNN9PjLOSFEDfSVkV1AtvdqUGpDmaYRCiw0WdUvDCudIpgg5yL7zfnePWh5ortuRoQJIT9OAGyvVLpaWPAT-hqHIhdasZnNbEdVu90Wm9QmAdbBXjrWKHpUYX4c-Z6dS6bXRKZwx0WvvWYbBRlXEKT79enu6f5j9-vTz-PseS5liC4I3nTi-6bQeAH3QYlfBovMZxiAfYWamdGt61Srbq4IiqLfRwDztFlVsznx-I1HGRF901J2-CpWZVOyjXJS2Tao0GuP_xmlRaskRDiiem4hvLDsRKJkaq2N_0RVtT9wL3hQttAr5ZbnpQ5C24DbNdojVv2ix1epays8zKe8UwnG49mNoI70n3a8RvzT0UBl3CUZcw3hFu7fpQbv75MvN3yusUTHAeJrgAZnQeZnQBTHweJj4Csw-2n_cu1GO6J6082EIvQt5VPg_d7LkXAbeq52HdFn0R7o7umUhvNvFu4I9aXTVgt_pLwILLwEYXgY0uA4svAos7IyepZTxpK9ns2_scwN2cHLFC5oG0IxFICfB3S4cgE7IhP9vt1yyLIHhv0DkFIdmScSQeduoKadwxbUgw5bRlZZKmdWIKTCu7Lw_2tqPHDNaiBkXeqF0FyRieOW5juKLhR7jXDhJLj-YISQolIDcTrAFP5BVvukiEcHHjA0bwjXJGeXKGG2m707cBTSw_REIqJcLsElMccNG3LBZ53pJDX4A1SkA_AWfezkJJQQnfhZYl9GXm5nQk6Y9aV_WGGjt7-miGYoLbVHT50-g7bfDDwXDgN5JnIpfU-Arv8eRlMupXSb9gvH7vL3ntVHJJSQol5rYwipVQ7N2lCCuSFAVN75g0Ii94qBVucA8FW5jv4q3EHx95yMOC8Q7vHi3hNVluqHhFkleyxOJYrOE3yrUQgyOlgZ2ErTNMsysBW41NpBAPayQTRSFW6pLwfC697jy8CU0uAhMNC2dOLL_PpCgxQNGRO0JzjUeG3ePPUVEqRaUcudm0FCgc3zqr0fndZmp813I58znNKDYa3vh-zxF_jF8j82XaLGo9eq-I6bMaZ0qSSGvxHnq0h_yFFPZffg6dDP1rZavpJL4mXcF3uly6gmuly3R0X5Os0XeyXLLCayXLdtZfk634O1suW8a_MPqf3biu0ZB-LiyTq4XlmneIa3TYn4tLdLW4XG8rvsYDg89FJb5aVK64513jAch_CUvcBEHBknIqiaapY_GWsdt-4aY5jC_bbs3dNGwTNr6De8vK_Y7u4UbZdiAhHBSlmz7APeMHwYs1aGxRl9j_wMq8gqiVewHReOtFt7hrzPEKmWM9zGPTLmPLaB7wKoNm3jIYxAVRdPdfaf9tYMxjkg6YAaCRqk7yplFd0IJR19cu6mXTbtuRfbRPEm0atQXVK0r5B29M7-xW_fByoHlB0bw_OHhJAL10FqbTcEp6mumCzuau49nWDDzuvPx43gQLbSDw7J5z_3CIZtyrZTHLta5sZxU84LFkOq8Xg0SUbednfvqVFH8iLg6ZUrWJ3cM4jONJL58FSeoHUTalw9iPUj_LFul0PJ7E0TSajJJx0CsIRkrNsDq8IOB0BRYCz7EwemwWDAM8_IkfjYfheDCOMp-G_nSSjSaTcBR4oyEtCSsGxo6BkMuenFmTMOQKhQVTWrVCouylR-1yiE9qjTv2bEneGM8FJiDt2eVn1vx_AKQSjmA">