我在Solaris 11.3上使用Developer Studio 12.5附帶的SunCC編譯器構建Botan。我對庫或Solaris不太熟悉,並且需要我花費一些努力來追蹤問題。GASM內部參數'N'的引用無效內聯
編譯死於一個相對良性的文件,稱爲divide.cpp
。我已經將它簡化爲以下測試用例。根據Oracle的GCC-style asm inlining support in Sun Studio 12 compilers,ASM格式良好。 Clang,GCC和ICC愉快地使用代碼。
$ /opt/developerstudio12.5/bin/CC -m64 -std=c++11 test.cxx -c
"test.cxx", [main]:ube: error: Invalid reference to argument '1' in GASM Inlining
CC: ube failed for test.cxx
$ cat test.cxx
#include <iostream>
#include <stdint.h>
typedef uint64_t word;
inline word multadd(word a, word b, word* c)
{
asm(
"mulq %[b] \n\t"
"addq %[c],%[a] \n\t"
"adcq $0,%[carry] \n\t"
: [a]"=a"(a), [b]"=rm"(b), [carry]"=&d"(*c)
: "0"(a), "1"(b), [c]"g"(*c) : "cc");
return a;
}
int main(int argc, char* argv[])
{
word a, b, c, d;
std::cin >> a >> b >> c;
d = multadd(a, b, &c);
return 0;
}
我找不到錯誤字符串Invalid reference to argument 'N' in GASM Inlining
有用的信息。我在Oracle主板上找到了sunCC chokes on inline assembler。但答案是UBE是越野車,併購買支持合同以瞭解更多信息。
我有三個問題:
是什麼錯誤消息說明什麼?
如何讓SunCC提供源文件和行號?
我該如何解決這個問題?
如果更改b
參數到剛=m
,則產生相同的錯誤。如果我改變b
參數只是=r
,則生成一個不同的錯誤:
asm(
"mulq %[b] \n\t"
"addq %[c],%[a] \n\t"
"adcq $0,%[carry] \n\t"
: [a]"=a"(a), [b]"=r"(b), [carry]"=&d"(*c)
: "0"(a), "1"(b), [c]"g"(*c) : "cc");
而結果:
$ /opt/developerstudio12.5/bin/CC -m64 -std=c++11 test.cxx -c
Assembler: test.cxx
"<null>", line 205 : Invalid instruction argument
Near line: "mulq %rcx "
"<null>", line 206 : Invalid instruction argument
Near line: " addq %rbx,%rax "
"<null>", line 207 : Invalid instruction argument
Near line: " adcq $0,%rdx "
CC: ube failed for test.cxx
如果這是gcc,我會建議使用'-S'來構建。它[看起來像](https://docs.oracle.com/cd/E19205-01/819-5265/6n7c29df6/index.html#6n7c29dmc)Suncc也可以支持這一點?確切地看到產生的東西在這裏確實有幫助。我也想知道使用'mull'和'addl'。最後一個'l'應該表示一個4字節的int,但是你傳遞了(我認爲是2字節)的單詞?你提供的博客鏈接指出,Sun的C++不能很好地處理「即時」操作數。 'g'可能意味着'我'。雖然沒有看到這是「論點1」。 –
較小的情況有幫助。你能把它變得更小嗎?使用''「'asm字符串怎麼樣?我的猜測是,它會證明你至少需要'仔細考慮%[b]'。 –
由於在編譯過程中出現問題,因此實際上不需要塊運行或產生相同的結果。一旦你將所需的asm修剪到仍然產生錯誤的最小值,你可以開始刪除參數。我在期待:'asm(「mull%[b]」:[b]「= rm」(b):「0」(b));'。 –