Eliot
Eliot

Reputation: 2429

C/C++ extension for Visual Studio Code, gcc, Mac: "variable uint32_t is not a type name"

I've begun using VSC for my embedded C projects with gcc for ARM on a Mac. Having set up include paths in c_cpp_properties.json, most of my #includes are now working. However, a line such as this:

uint32_t m_ttff_seconds = 0;

produces a red squiggly underline and the error:

variable uint32_t is not a type name

The source file in question includes stdint:

#include <stdint.h>

and the includePath includes:

"${HOME}/dev/gcc-arm-none-eabi-4_9-2015q3/lib/gcc/arm-none-eabi/4.9.3/include"

and:

"intelliSenseMode": "clang-x64"

(the only other option being msvc-x64).

The codebase compiles just fine when I use make and gcc. How do I show the C/C++ extension where uint32_t is?

Edit:

stdint.h looks like this:

#ifndef _GCC_WRAP_STDINT_H
#if __STDC_HOSTED__
# if defined __cplusplus && __cplusplus >= 201103L
#  undef __STDC_LIMIT_MACROS
#  define __STDC_LIMIT_MACROS
#  undef __STDC_CONSTANT_MACROS
#  define __STDC_CONSTANT_MACROS
# endif
# include_next <stdint.h>
#else
# include "stdint-gcc.h"
#endif
#define _GCC_WRAP_STDINT_H
#endif

and stdint-gcc.h contains:

/* 7.8.1.1 Exact-width integer types */

#ifdef __INT8_TYPE__
typedef __INT8_TYPE__ int8_t;
#endif
#ifdef __INT16_TYPE__
typedef __INT16_TYPE__ int16_t;
#endif
#ifdef __INT32_TYPE__
typedef __INT32_TYPE__ int32_t;
#endif
#ifdef __INT64_TYPE__
typedef __INT64_TYPE__ int64_t;
#endif
#ifdef __UINT8_TYPE__
typedef __UINT8_TYPE__ uint8_t;
#endif
#ifdef __UINT16_TYPE__
typedef __UINT16_TYPE__ uint16_t;
#endif
#ifdef __UINT32_TYPE__
typedef __UINT32_TYPE__ uint32_t;
#endif
#ifdef __UINT64_TYPE__
typedef __UINT64_TYPE__ uint64_t;
#endif

This suggests __UINT32_TYPE__ is NOT defined when VSC is parsing my code, but it IS defined when I build with make and gcc.

Edit:

Following @mbmcavoy's answer I'm including my c_cpp_properties.json file here:

{
    "configurations": [
        {
            "name": "Mac",
            "includePath": [
                "${HOME}/dev/gcc-arm-none-eabi-4_9-2015q3/lib/gcc/arm-none-eabi/4.9.3/include",
                "${HOME}/dev/nRF5_SDK_14.0.0_3bcc1f7/components/libraries/util",
                "${HOME}/dev/nRF5_SDK_14.0.0_3bcc1f7/config",
                [many more of these omitted]
                "${HOME}/dev/wisol_SDK_SFM20Rx_master/development/sigfox_cfg2/source",
                "${workspaceRoot}"
            ],
            "browse": {
                "path": [
                    "${HOME}/dev/gcc-arm-none-eabi-4_9-2015q3/lib/gcc/arm-none-eabi/4.9.3/include",
                    "${HOME}/dev/nRF5_SDK_14.0.0_3bcc1f7/components/libraries/util",
                    "${HOME}/dev/nRF5_SDK_14.0.0_3bcc1f7/config",
                    [many more of these omitted]
                    "${workspaceRoot}"
                ],
                "databaseFilename": "${workspaceRoot}/.vscode/browse.vc.db"
            },
            "intelliSenseMode": "clang-x64",
            "macFrameworkPath": [
                "/System/Library/Frameworks",
                "/Library/Frameworks"
            ],
            "defines": [
                "__UINT_LEAST16_MAX__=65535",
                "__UINT_LEAST8_TYPE__=unsigned char",
                "__UINT8_MAX__=255",
                "__UINT_FAST64_MAX__=18446744073709551615ULL",
                "__UINT_FAST8_MAX__=4294967295U",
                "__UINT_LEAST64_MAX__=18446744073709551615ULL",
                "__UINT_LEAST8_MAX__=255",
                "__UINTMAX_TYPE__=long long unsigned int",
                "__UINT32_MAX__=4294967295UL",
                "__UINT16_C(c)=c",
                "__UINT16_MAX__=65535",
                "__UINT8_TYPE__=unsigned char",
                "__UINT64_C(c)=c ## ULL",
                "__UINT_LEAST16_TYPE__=short unsigned int",
                "__UINT64_MAX__=18446744073709551615ULL",
                "__UINTMAX_C(c)=c ## ULL",
                "__UINT_FAST32_MAX__=4294967295U",
                "__UINT_LEAST64_TYPE__=long long unsigned int",
                "__UINT_FAST16_TYPE__=unsigned int",
                "__UINT_LEAST32_MAX__=4294967295UL",
                "__UINT16_TYPE__=short unsigned int",
                "__UINTPTR_MAX__=4294967295U",
                "__UINT_FAST64_TYPE__=long long unsigned int",
                "__UINT_LEAST32_TYPE__=long unsigned int",
                "__UINT8_C(c)=c",
                "__UINT64_TYPE__=long long unsigned int",
                "__UINT32_C(c)=c ## UL",
                "__UINT_FAST32_TYPE__=unsigned int",
                "__UINTMAX_MAX__=18446744073709551615ULL",
                "__UINT32_TYPE__=long unsigned int",
                "__UINTPTR_TYPE__=unsigned int",
                "__UINT_FAST16_MAX__=4294967295U",
                "__UINT_FAST8_TYPE__=unsigned int"
            ]
        }
    ],
    "version": 3
}

Edit:

On digging deeper, I found that gcc-arm-none-eabi-4_9-2015q3/lib/gcc/arm-none-eabi/4.9.3/include/stdint.h had __STDC_HOSTED__ defined and therefore stdint-gcc.h was not actually being included. Instead, that header does an "include_next <stdint.h>", which finds gcc-arm-none-eabi-4_9-2015q3/arm-none-eabi/include/stdint.h. I still can't see where unint32_t is defined, either for gcc and make or for VSC.

Upvotes: 6

Views: 6086

Answers (2)

gekart
gekart

Reputation: 173

After trying all of the proposed solutions to no effect, I consider the uint32_t issue to be a bug.

To solve the annoying warnings in VSCode, just add the following line after your #include section:

typedef __uint32_t uint32_t;

By doing this once in a single file, it fixes my VSCode warnings and still compiles.

Upvotes: 3

mbmcavoy
mbmcavoy

Reputation: 2686

I have been able to resolve this on my machine (Windows), with three steps:

  1. Applying Compiler Defines to the C/C++ Extension

The question is correct when it states "This suggests __UINT32_TYPE__ is NOT defined when VSC is parsing my code, but it IS defined when I build with make and gcc." The ARM cross-compiler has many built-in defines that are not included in the clang-x64 parser.

First, find out defines your gcc compiler defines, with the -dM -E options. On Windows I was able to dump the output to a file with echo | arm-none-eabi-gcc -dM -E - > gcc-defines.txt

#define __DBL_MIN_EXP__ (-1021)
#define __HQ_FBIT__ 15
#define __UINT_LEAST16_MAX__ 0xffff
#define __ARM_SIZEOF_WCHAR_T 4
#define __ATOMIC_ACQUIRE 2
#define __SFRACT_IBIT__ 0
#define __FLT_MIN__ 1.1754943508222875e-38F
#define __GCC_IEC_559_COMPLEX 0
(etc. - I have 344 defines)

Second, add the defines to your c_cpp_properties.json file. Note that where the #define sets a value, you need to use an = sign here. (You could probably just add individual defines as you need them, but I used Excel to format them as needed and sort. The first defines are for my project, matching the defines in my Makefile.)

"defines": [
    "STM32F415xx",
    "USE_FULL_LL_DRIVER",
    "__USES_INITFINI__",
    "__ACCUM_EPSILON__=0x1P-15K",
    "__ACCUM_FBIT__=15",
    (...)
    "__UINT32_TYPE__=long unsigned int",
    (etc.)
  1. Setting the Symbol Database

After doing a few experiments with individual defines, I could see the define as being processed in stdint-gcc.h, any uses of the types still produced errors. I realized in my c_cpp_properties.json file that I had "databaseFilename": "" This is used for the "generated symbol database", but was not configured properly. I set it to:

"databaseFilename": "${workspaceRoot}/.vscode/browse.vc.db"
  1. Restart Visual Studio Code

After quitting and restarting Visual Studio Code, declarations do not result in the error, and when hovering over a variable, it shows the appropriate type.

Upvotes: 1

Related Questions