Sebi
Sebi

Reputation: 4522

error C2440: 'initializing': cannot convert from 'const char *' to 'TCHAR *'

In a multibyte project (vs2017):

#ifndef _TCHAR_DEFINED
typedef char            TCHAR;
typedef char *          PTCHAR;
typedef unsigned char   TBYTE;
typedef unsigned char * PTBYTE;
#define _TCHAR_DEFINED

struct _getopt_data
{
    /* These have exactly the same meaning as the corresponding global
       variables, except that they are used for the reentrant
       versions of getopt.  */
int optind;
int opterr;
int optopt;
TCHAR *optarg;

/* Internal members.  */

/* True if the internal members have been initialized.  */
int __initialized;

/* The next char to be scanned in the option-element
   in which the last option character we returned was found.
   This allows us to pick up the scan where we left off.

   If this is zero, or a null string, it means resume the scan
   by advancing to the next ARGV-element.  */
TCHAR *__nextchar;

/* Describe how to deal with options that follow non-option ARGV-elements.

   If the caller did not specify anything,
   the default is REQUIRE_ORDER if the environment variable
   POSIXLY_CORRECT is defined, PERMUTE otherwise.

   REQUIRE_ORDER means don't recognize them as options;
   stop option processing when the first non-option is seen.
   This is what Unix does.
   This mode of operation is selected by either setting the environment
   variable POSIXLY_CORRECT, or using `+' as the first character
   of the list of option characters.

   PERMUTE is the default.  We permute the contents of ARGV as we
   scan, so that eventually all the non-options are at the end.
   This allows options to be given in any order, even with programs
   that were not written to expect this.

   RETURN_IN_ORDER is an option available to programs that were
   written to expect options and other ARGV-elements in any order
   and that care about the ordering of the two.  We describe each
   non-option ARGV-element as if it were the argument of an option
   with character code 1.  Using `-' as the first character of the
   list of option characters selects this mode of operation.

   The special argument `--' forces an end of option-scanning regardless
   of the value of `ordering'.  In the case of RETURN_IN_ORDER, only
   `--' can cause `getopt' to return -1 with `optind' != ARGC.  */

enum
{
    REQUIRE_ORDER, PERMUTE, RETURN_IN_ORDER
} __ordering;

/* If the POSIXLY_CORRECT environment variable is set.  */
int __posixly_correct;


/* Handle permutation of arguments.  */

/* Describe the part of ARGV that contains non-options that have
   been skipped.  `first_nonopt' is the index in ARGV of the first
   of them; `last_nonopt' is the index after the last of them.  */

int __first_nonopt;
int __last_nonopt;

#if defined _LIBC && defined USE_NONOPTION_FLAGS
    int __nonoption_flags_max_len;
    int __nonoption_flags_len;
# endif
};

int
_getopt_internal_r(int argc, TCHAR *const *argv, const TCHAR *optstring,
    const struct option *longopts, int *longind,
    int long_only, struct _getopt_data *d, int posixly_correct)
{
 ... 
 TCHAR c = *d->__nextchar++;
 TCHAR *temp = _tcschr(optstring, c); // <= cannot convert from 'const char *' to 'TCHAR *' (first parameter) 
 ...
}

Everything looks correct; in tchar.h:

#define _PUC    unsigned char *
#define _CPUC   const unsigned char *
#define _PC     char *
#define _CRPC   _CONST_RETURN char *
#define _CPC    const char *
#define _UI     unsigned int


/* String functions */

__inline _CRPC _tcschr(_In_z_ _CPC _s1,_In_ _UI _c) {return (_CRPC)_mbschr((_CPUC)_s1,_c);}

Why is _tcschr() complaining that a parameter is not of const char*, when it is?

Upvotes: 0

Views: 1818

Answers (1)

Remy Lebeau
Remy Lebeau

Reputation: 595320

In C++, _tcschr() is overloaded to take either a TCHAR* or a const TCHAR* as input. To return a non-const TCHAR*, you will have to call the non-const overload, which means casting away the const off of optstring, eg:

TCHAR *temp = _tcschr(const_cast<TCHAR*>(optstring), c);

Or else define _CONST_RETURN, per the documentation:

In C, these functions take a const pointer for the first argument. In C++, two overloads are available. The overload taking a pointer to const returns a pointer to const; the version that takes a pointer to non-const returns a pointer to non-const. The macro _CRT_CONST_CORRECT_OVERLOADS is defined if both the const and non-const versions of these functions are available. If you require the non-const behavior for both C++ overloads, define the symbol _CONST_RETURN.

Upvotes: 2

Related Questions