g ++를 사용하여 null const char*를 사용한 부적절한 std :: 문자열 초기화를 피하십시오.

StackOverflow https://stackoverflow.com/questions/2407711

  •  18-09-2019
  •  | 
  •  

문제

a g ++ 옵션이있는 옵션이 널 const char*로 std :: 문자열의 부적절한 초기화를 감지 할 수 있습니까?

나는 int 필드를 std :: 문자열로 바꾸는 과정에있었습니다.

struct Foo
{
   int id;
   Foo() : id(0) {} 
};

...로 전환:

struct Foo
{
   std::string id;
   Foo() : id(0) {} //oooops!
};

0으로 BAD 'ID'초기화를 완전히 간과하고 G ++는 전혀 경고를주지 않았습니다. 이 오류는 런타임에 감지되었지만 (std :: 문자열 생성자는 예외를 던졌습니다) 컴파일 시간에서 그러한 것들을 감지하고 싶습니다. 어떤 방법이 있습니까?

도움이 되었습니까?

해결책

나는 그것이 실제로 정의되지 않은 동작이며 컴파일러에 의해 점검되지 않았다고 생각합니다. 이 구현이 예외를 던진다는 것이 운이 좋다.

그러나 타입 공유 방식으로 기본 또는 제로 시작을 원하는 것을 지정하여 이러한 문제를 피할 수 있습니다.

struct Foo
{
   X id;
   Foo() : id() {} //note empty parenthesis
};

다른 팁

컴파일 타임에서 이것을 감지하는 방법을 생각할 수 없으므로 널 포인터를 제대로 다루는 문자열 빌더 기능을 작성했습니다.

//  FUNCTION :      safe_string(char const* pszS)
//  PARAMATERS :    pszS        source string to build a string from (may be NULL or 0-length)
//  DESCRIPTION :   Safely builds a string object from a char*, even a NULL pointer
//  RETURNS :       string

template<class C>
inline basic_string<C> safe_string(const C* input)
{
    if( !input )
        return basic_string<C>();
    return basic_string<C>(input);
}

문자열을 만들 때마다 이것을 사용하고 입력이 null 일 가능성이 있습니다.

GCC에는 이러한 종류의 경고를 정확히 생성하기위한 인프라가 있습니다.

void foo(const char* cstr) __attribute__((nonnull (1)));

void bar() {
    foo(0);
}

컴파일 된 경우 -Wnonnull (암시된다 -Wall) 제작 :

warning: null argument where non-null required (argument 1)

따라서 원칙적으로 관련 시스템 헤더를 수정할 수 있어야합니다 (또는 실험에 더 나은 경우 자신의 $ 홈/비트/Basic_string.h 복사 한 다음 시스템을 재정의하십시오. -isystem $HOME) 마찬가지로 :

basic_string(const _CharT* __s, const _Alloc& __a = _Alloc())
    __attribute__((nonnull (1)));

그러나 이것은 (적어도 4.0.1에서) 도움이되지 않습니다. -Wnonnull C ++에서는 지원되지 않으며 속성은 분명히 무시됩니다. 이것이 왜 그렇게되는지 분명하지 않습니다. 아마도 그것은 과부하 나 무언가와 심하게 상호 작용한다고 느꼈을 것입니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top