2016-03-28 109 views
2

不工作編譯與SDL檢查發佈配置下面的代碼無效:編譯警告(禁用:4700)在Visual Studio Express的2013

#include <immintrin.h> 

int main() 
{ 
    const auto Set128Epi16 = []() 
    { 
#ifdef NDEBUG 
#pragma warning(push) 
#pragma warning(disable : 4700) 
      __m128i x = _mm_cmpeq_epi16(x,x); 
      x = _mm_srli_epi16(x,15); 
      return _mm_slli_epi16(x,7); 
#pragma warning(pop) 
#else 
      __m128i x = _mm_setzero_si128(); 
      x = _mm_cmpeq_epi16(x,x); 
      x = _mm_srli_epi16(x,15); 
      return _mm_slli_epi16(x,7); 
#endif 
    }; 

    const auto xmm = Set128Epi16(); 

    return *xmm.m128i_i32; 
} 

給出了以下的輸出:

1>------ Rebuild All started: Project: pragmatic, Configuration: Release Win32 ------ 
1> main.cpp 
1> Generating code 
1>e:\projects\pragmatic\pragmatic\main.cpp(10): warning C4700: uninitialized local variable 'x' used 
1>e:\projects\pragmatic\pragmatic\main.cpp(10): warning C4700: uninitialized local variable 'x' used 
1>e:\projects\pragmatic\pragmatic\main.cpp(10): warning C4700: uninitialized local variable 'x' used 
1>e:\projects\pragmatic\pragmatic\main.cpp(10): warning C4700: uninitialized local variable 'x' used 
1>e:\projects\pragmatic\pragmatic\main.cpp(10): warning C4700: uninitialized local variable 'x' used 
1> Finished generating code 
1> pragmatic.vcxproj -> E:\Projects\pragmatic\Release\pragmatic.exe 
========== Rebuild All: 1 succeeded, 0 failed, 0 skipped ========== 

爲什麼編譯器在這種情況下忽略我的#pragma。我在過去成功地使用這種方法來抑制相同的警告代碼。

+0

你爲什麼試圖比較一個未初始化的變量與自身的值?你確實意識到這有未定義的行爲?據我所知,基本上沒有實際用途?也許你可以更多地解釋你在這裏做的實際情況。 –

+0

它被報告爲VS2015中的錯誤。適當地,_mm_cmpeq_epi16()的參數未被初始化。很難猜測這裏有什麼意思,x和x應該等於任何值:) –

+0

@BarryTheHatchet這是一個相當常見的技巧,用於將0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF加載到xmm寄存器中。認爲pxor xmm0,xmm0。寄存器的內容對結果沒有影響。 – chili

回答

1

我複製這個從https://msdn.microsoft.com/en-us/library/2c8f766e.aspx

對於範圍內4700-4999,這與代碼產生相關聯的那些警告號,生效的警告的狀態下,當編譯器遇到的大括號一個函數將對該函數的其餘部分有效。使用函數中的警告附註更改數字大於4699的警告的狀態只會在函數結束後生效。以下示例顯示警告編譯指示的正確位置以禁用代碼生成警告消息,然後將其還原。

因此,您可能需要在main開始之前或者在lambda工作之前放置雜注,但我不確定這一點。

+0

在lambda工作之前像魅力一樣。 – chili

相關問題