วิธีการดูว่าธง --march = พื้นเมืองจะเปิดใช้งาน?


165

ฉันกำลังรวบรวมแอป C ++ ของฉันโดยใช้ GCC 4.3 แทนที่จะเลือกการตั้งค่าสถานะการปรับแต่งที่ฉันใช้ด้วยตนเอง-march=nativeซึ่งในทางทฤษฎีแล้วควรเพิ่มการตั้งค่าสถานะการปรับให้เหมาะสมทั้งหมดที่ใช้กับฮาร์ดแวร์ที่ฉันกำลังรวบรวม แต่ฉันจะตรวจสอบการตั้งค่าสถานะที่ใช้งานจริงได้อย่างไร

คำตอบ:


150

คุณสามารถใช้-Q --help=targetตัวเลือก:

gcc -march=native -Q --help=target ...

-vตัวเลือกนอกจากนี้ยังอาจจะมีการใช้

คุณสามารถดูเอกสารใน--helpตัวเลือกที่นี่


10
ฉันจะแนะนำว่านี่เป็นสิ่งที่ไม่ดี ผลลัพธ์ของ --help = target ไม่แสดงข้อมูลแคช CPU ซึ่งมีวิธีการทั้ง elias และ 42n4 ด้านล่างแสดงอยู่ โดยเฉพาะใน gcc 4.9.2 ใน Phenom ผลลัพธ์จะรวมสิ่งเหล่านี้:--param l1-cache-size=64 --param l1-cache-line-size=64 --param l2-cache-size=512
Daniel Santos

@DanielSantos: ในระบบของฉันมันไม่แสดงพารามิเตอร์ผู้ที่มี-vตัวเลือกที่แม้จะเป็นส่วนหนึ่งของcc1บรรทัดคำสั่ง ...
thkala

ไม่สมบูรณ์แบบ บน gcc เวอร์ชั่น 5.4.0 (Buildroot 2017.05-rc2-00016-gc7eaf50-สกปรก) มันจะทำให้เกิดข้อผิดพลาดในการกลับมา: ข้อความประกอบ: ข้อผิดพลาด: สถาปัตยกรรมที่ไม่รู้จักข้อผิดพลาด: พื้นเมืองตัวเลือกที่ไม่รู้จัก -march = native ดังนั้นหลวมและมันจะทำงานได้ทุกที่เพียงแค่ต่อไปนี้:-march=native gcc -Q --help=target
Oleg Kokorin

@Oleg - ฟังดูเหมือนเป็นข้อบกพร่องใน GCC 5. ไม่มีปัญหาใน GCC 7
jww

111

ในการดูการตั้งค่าสถานะบรรทัดคำสั่งให้ใช้:

gcc -march=native -E -v - </dev/null 2>&1 | grep cc1

หากคุณต้องการเห็นคอมไพเลอร์ / พรีคอมไพเลอร์กำหนดโดยพารามิเตอร์ที่กำหนดให้ทำ:

echo | gcc -dM -E - -march=native

1
คำตอบนี้สมควรได้รับ upvotes มากที่สุดเท่าที่เป็นที่ยอมรับโดยเฉพาะในรายการสิ่งที่nativeเท่ากับ
Iwillnotexist Idonotexist

4
ดังนั้นหากฉันต้องการข้ามคอมไพล์ฉันควรป้อนทั้งคอมไพเลอร์ทั้งกำหนดและอาร์กิวเมนต์? หรือมีข้อโต้แย้งเพียงพอ
hanshenrik

25

มันควรจะเป็น ( -###คล้ายกับ-v):

echo | gcc -### -E - -march=native 

หากต้องการแสดงแฟล็กดั้งเดิม "ของจริง" สำหรับ gcc

คุณสามารถทำให้พวกเขาปรากฏขึ้น "ชัดเจน" ด้วยคำสั่ง:

gcc -### -E - -march=native 2>&1 | sed -r '/cc1/!d;s/(")|(^.* - )//g'

และคุณสามารถกำจัดธงด้วย -mno- * ด้วย:

gcc -### -E - -march=native 2>&1 | sed -r '/cc1/!d;s/(")|(^.* - )|( -mno-[^\ ]+)//g'

10

หากคุณต้องการทราบวิธีการตั้งค่าการรวบรวมข้ามที่ไม่ใช่เจ้าของภาษาฉันพบว่ามีประโยชน์นี้:

บนเครื่องเป้าหมาย

% gcc -march=native -Q --help=target | grep march
-march=                               core-avx-i

จากนั้นใช้สิ่งนี้กับเครื่องสร้าง:

% gcc -march=core-avx-i ...

นี้จะไม่รวมถึงธงทั้งหมดอย่างน่าเสียดาย
Baptiste Wicht

@BaptisteWicht มีแฟล็กที่ -march = native จะรวมถึง -march = core-avx-i ในกรณีนี้หรือว่าจะเป็นแฟล็กใด ขอบคุณ!
rogerdpack

2
@rogerdpack บนคอมพิวเตอร์เครื่องนี้ (sandybridge), march = sandybridge ไม่เปิดใช้งาน AVX (ไม่รู้ว่าทำไม) ในขณะที่ march = native ไม่ทำงาน ข้อแตกต่างที่สำคัญอีกอย่างคือขนาดแคชจะถูกแยกด้วยมีนาคมเท่านั้น
Baptiste Wicht

1
@ BaptisteWich ที่แปลกดูเหมือนว่าจะทำงานที่นี่ (ฉันเดา): echo | gcc-6 -dM -E - -march=sandybridge | grep AVX #define __AVX__ 1แต่ขนาดแคชดูเหมือนจะขาด
rogerdpack

7

ฉันจะโยนสองเซ็นต์ของฉันเป็นคำถามนี้และแนะนำการขยายคำตอบของ elias ที่ละเอียดขึ้นเล็กน้อย ตั้งแต่ gcc 4.6 มีการgcc -march=native -v -E - < /dev/nullปล่อยสแปมจำนวนมากขึ้นในรูปแบบของ-mno-*สถานะที่ไม่จำเป็น ดังต่อไปนี้จะตัดสิ่งเหล่านี้:

gcc -march=native -v -E - < /dev/null 2>&1 | grep cc1 | perl -pe 's/ -mno-\S+//g; s/^.* - //g;'

อย่างไรก็ตามฉันได้ตรวจสอบความถูกต้องของสิ่งนี้กับซีพียูสองตัวที่แตกต่างกัน (Intel Core2 และ AMD Phenom) ดังนั้นฉันขอแนะนำให้รันสคริปต์ต่อไปนี้เพื่อให้แน่ใจว่า-mno-*แฟล็กเหล่านี้ทั้งหมดสามารถถอดได้อย่างปลอดภัย

#!/bin/bash

gcc_cmd="gcc"

# Optionally supply path to gcc as first argument
if (($#)); then
    gcc_cmd="$1"
fi

with_mno=$(
    "${gcc_cmd}" -march=native -mtune=native -v -E - < /dev/null 2>&1 |
    grep cc1 |
    perl -pe 's/^.* - //g;'
)
without_mno=$(echo "${with_mno}" | perl -pe 's/ -mno-\S+//g;')

"${gcc_cmd}" ${with_mno}    -dM -E - < /dev/null > /tmp/gcctest.a.$$
"${gcc_cmd}" ${without_mno} -dM -E - < /dev/null > /tmp/gcctest.b.$$

if diff -u /tmp/gcctest.{a,b}.$$; then
    echo "Safe to strip -mno-* options."
else
    echo
    echo "WARNING! Some -mno-* options are needed!"
    exit 1
fi

rm /tmp/gcctest.{a,b}.$$

ฉันไม่พบความแตกต่างระหว่างgcc -march=native -v -E - < /dev/nullและgcc -march=native -### -E - < /dev/nullนอกเหนือจากพารามิเตอร์บางอย่างที่อ้างถึง - และพารามิเตอร์ที่ไม่มีอักขระพิเศษดังนั้นฉันไม่แน่ใจว่าภายใต้สถานการณ์ใดที่ทำให้เกิดความแตกต่างที่แท้จริง

ในที่สุดโปรดทราบว่า--march=nativeมีการนำมาใช้ใน gcc 4.2 ก่อนหน้านี้ซึ่งเป็นเพียงอาร์กิวเมนต์ที่ไม่รู้จัก


ดี gleans นี้มีขนาดแคชเช่นกัน
rogerdpack

gcc เวอร์ชั่น 5.4.0 (Buildroot 2017.05-rc2-00016-gc7eaf50-สกปรก) ผลตอบแทน: ข้อผิดพลาด: สถาปัตยกรรมที่ไม่รู้จัก `native '
Oleg Kokorin

Oleg: คุณใช้ซุ้มประตูอะไร อาจเป็นไปได้ว่า "native" รองรับเฉพาะในบางสถาปัตยกรรมเท่านั้น
Daniel Santos
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.