C++ टूलचेन कॉन्फ़िगरेशन

समस्या की शिकायत करें सोर्स देखें ठीक

खास जानकारी

कंपाइलर को सही विकल्पों के साथ शुरू करने के लिए, बेज़ेल को कंपाइलर इंंटरनल के बारे में कुछ जानकारी की ज़रूरत होती है, जैसे कि डायरेक्ट्री और ज़रूरी फ़्लैग शामिल करने की जानकारी. दूसरे शब्दों में, बेज़ल को कंपाइलर के काम करने के तरीके को समझने के लिए, कंपाइलर के एक आसान मॉडल की ज़रूरत होती है.

बेज़ल को यह जानकारी होनी चाहिए:

  • कंपाइलर थिनएलटीओ, मॉड्यूल, डाइनैमिक लिंकिंग या पीआईसी के साथ काम करता है या नहीं (पोज़िशन इंडिपेंडेंट कोड).
  • gcc, ld, ar, objcopy जैसे ज़रूरी टूल तक पहुंचने के लिए पाथ.
  • बिल्ट-इन सिस्टम में डायरेक्ट्री शामिल होती हैं. Baज़र के लिए इनकी ज़रूरत होती है, ताकि इस बात की पुष्टि की जा सके कि सोर्स फ़ाइल में शामिल सभी हेडर, BUILD फ़ाइल में सही तरीके से एलान किए गए थे.
  • डिफ़ॉल्ट सिस्टम.
  • कंपाइलेशन, लिंक करने, संग्रहित करने के लिए किन फ़्लैग का इस्तेमाल करना है.
  • काम करने वाले कंपाइलेशन मोड (ऑप्ट, डीबीजी, फ़ास्टबिल्ड) के लिए किन फ़्लैग का इस्तेमाल करना है.
  • कंपाइलर के लिए खास तौर पर ज़रूरी वैरिएबल बनाएं.

अगर कंपाइलर के पास एक से ज़्यादा आर्किटेक्चर का इस्तेमाल करने की सुविधा है, तो बेज़ेल को उन्हें अलग-अलग कॉन्फ़िगर करना होगा.

CcToolchainConfigInfo एक ऐसी कंपनी है जो Baze के C++ नियमों के व्यवहार को कॉन्फ़िगर करने के लिए, ज़रूरी जानकारी मुहैया कराती है. डिफ़ॉल्ट रूप से, Baze आपके बिल्ड के लिए CcToolchainConfigInfo को अपने-आप कॉन्फ़िगर कर देता है. हालांकि, आपके पास इसे मैन्युअल तरीके से कॉन्फ़िगर करने का विकल्प होता है. इसके लिए, आपको स्टारलार्क नियम की ज़रूरत है, जो CcToolchainConfigInfo देता हो. साथ ही, आपको cc_toolchain के toolchain_config एट्रिब्यूट को अपने नियम पर ले जाना होगा. cc_common.create_cc_toolchain_config_info() को कॉल करके CcToolchainConfigInfo बनाया जा सकता है. @rules_cc//cc:cc_toolchain_config_lib.bzl में आपको उन सभी स्ट्रक्चर के लिए Starlark कंस्ट्रक्टर मिल जाएंगे जिनकी इस प्रोसेस में ज़रूरत होगी.

जब कोई C++ टारगेट, विश्लेषण के चरण में आता है, तो Baze, BUILD फ़ाइल के आधार पर सही cc_toolchain टारगेट चुनता है. साथ ही, cc_toolchain.toolchain_config एट्रिब्यूट में दिए गए टारगेट से CcToolchainConfigInfo सेवा देने वाली कंपनी हासिल करता है. cc_toolchain टारगेट, इस जानकारी को CcToolchainProvider के ज़रिए C++ टारगेट को भेजता है.

उदाहरण के लिए, cc_binary या cc_library जैसे नियम से इंस्टैंशिएट की जाने वाली, कंपाइल या लिंक ऐक्शन में यह जानकारी होनी चाहिए:

  • इस्तेमाल करने के लिए कंपाइलर या लिंकर
  • कंपाइलर/लिंकर के लिए कमांड-लाइन फ़्लैग
  • कॉन्फ़िगरेशन फ़्लैग को --copt/--linkopt विकल्पों से पास किया गया है
  • एनवायरमेंट वैरिएबल
  • सैंडबॉक्स में ऐसी आर्टफ़ैक्ट जिनमें कार्रवाई पूरी होती है

सैंडबॉक्स में ज़रूरी आर्टफ़ैक्ट को छोड़कर, ऊपर दी गई सभी जानकारी Starlark के उस टारगेट में बताई गई है जिसके बारे में cc_toolchain, बताता है.

सैंडबॉक्स में भेजे जाने वाले आर्टफ़ैक्ट के बारे में cc_toolchain टारगेट में बताया गया है. उदाहरण के लिए, cc_toolchain.linker_files एट्रिब्यूट की मदद से सैंडबॉक्स में भेजने के लिए, लिंकर बाइनरी और टूलचेन लाइब्रेरी के बारे में बताया जा सकता है.

टूलचेन चुनना

टूलचेन को चुनने का लॉजिक इस तरह काम करता है:

  1. उपयोगकर्ता, BUILD फ़ाइल में cc_toolchain_suite का टारगेट तय करता है और --crosstool_top विकल्प का इस्तेमाल करके, बैज को टारगेट पर पॉइंट करता है.

  2. cc_toolchain_suite टारगेट में कई टूलचेन का इस्तेमाल होता है. --cpu और --compiler फ़्लैग की वैल्यू से यह तय होता है कि इनमें से कौनसे टूलचेन को चुना जाएगा. ऐसा सिर्फ़ --cpu फ़्लैग की वैल्यू के आधार पर या जॉइंट --cpu | --compiler वैल्यू के आधार पर किया जाता है. चुनने की प्रोसेस इस तरह है:

    • अगर --compiler का विकल्प चुना गया है, तो Basel, cc_toolchain_suite.toolchains एट्रिब्यूट से उससे जुड़ी एंट्री को --cpu | --compiler वाली वैल्यू से चुनता है. अगर Basel को कोई संबंधित एंट्री नहीं मिलती है, तो एक गड़बड़ी की सूचना मिलती है.

    • अगर --compiler का विकल्प नहीं चुना गया है, तो Basel, cc_toolchain_suite.toolchains एट्रिब्यूट से उससे जुड़ी एंट्री को सिर्फ़ --cpu का इस्तेमाल करके चुनता है.

    • अगर कोई फ़्लैग नहीं दिया जाता है, तो Basel, होस्ट सिस्टम की जांच करता है और उनसे मिली जानकारी के आधार पर --cpu वैल्यू चुनता है. जांच करने के तरीके का कोड देखें.

टूलचेन चुनने के बाद, Starlark नियम में मौजूद feature और action_config ऑब्जेक्ट, बिल्ड (यानी कि बाद में बताए गए आइटम) के कॉन्फ़िगरेशन को कंट्रोल करते हैं. इन मैसेज की मदद से, बैजल बाइनरी में बदलाव किए बिना, Basel में C++ की पूरी तरह से डेवलप की गई सुविधाएं लागू की जा सकती हैं. C++ के नियमों में, ऐसी कई यूनीक कार्रवाइयां की जा सकती हैं जिनके बारे में बेज़ल सोर्स कोड में विस्तार से बताया गया है.

सुविधाएं

सुविधा ऐसी इकाई होती है जिसके लिए कमांड-लाइन फ़्लैग, कार्रवाइयां, एक्ज़ीक्यूशन एनवायरमेंट की सीमाओं या डिपेंडेंसी में बदलाव की ज़रूरत होती है. एक सुविधा, BUILD फ़ाइलों को treat_warnings_as_errors जैसे फ़्लैग के कॉन्फ़िगरेशन चुनने की अनुमति देने जैसी आसान सुविधा हो सकती है. इसके अलावा, C++ के नियमों के साथ इंटरैक्ट करने और कंपाइलेशन में header_modules या thin_lto जैसी नई कंपाइल ऐक्शन और इनपुट शामिल करने की अनुमति भी दी जा सकती है.

आम तौर पर, CcToolchainConfigInfo में सुविधाओं की एक सूची होती है जिसमें हर सुविधा में एक या उससे ज़्यादा फ़्लैग ग्रुप होते हैं. हर सुविधा के हिसाब से फ़्लैग की ऐसी सूची दी जाती है जो 'बेज़ल' से जुड़ी खास कार्रवाइयों पर लागू होती है.

किसी सुविधा का नाम पहले से मौजूद होता है, जिसकी मदद से Starlark के नियम कॉन्फ़िगरेशन को बेज़ेल रिलीज़ से पूरी तरह से अलग किया जा सकता है. दूसरे शब्दों में कहें, तो जब तक उन कॉन्फ़िगरेशन में नई सुविधाओं का इस्तेमाल करने की ज़रूरत नहीं होगी, तब तक Basel की रिलीज़, CcToolchainConfigInfo कॉन्फ़िगरेशन के काम करने के तरीके पर असर नहीं डालती है.

सुविधा को इनमें से किसी एक तरीके से चालू किया जाता है:

  • सुविधा के enabled फ़ील्ड को true पर सेट किया गया है.
  • बेज़ल या नियम के मालिक ने इसे साफ़ तौर पर चालू किया हो.
  • उपयोगकर्ता इसे --feature बेज़ल विकल्प या features नियम एट्रिब्यूट का इस्तेमाल करके चालू करता है.

सुविधाएं एक-दूसरे पर निर्भर हो सकती हैं. ये कमांड लाइन फ़्लैग, BUILD फ़ाइल सेटिंग, और दूसरे वैरिएबल पर निर्भर करती हैं.

सुविधाओं के साथ ऐसेट जोड़ना

आम तौर पर, डिपेंडेंसी को सीधे Basel की मदद से मैनेज किया जाता है. इससे, सिर्फ़ ज़रूरी शर्तों को लागू किया जाता है और बिल्ड में बताई गई सुविधाओं से जुड़े विवादों को मैनेज किया जाता है. टूलचेन की खास जानकारी से, Starlark के नियम में ज़्यादा बारीकियों का इस्तेमाल किया जा सकता है. नियमों में, सुविधा के इस्तेमाल और उसका दायरा बढ़ाने से जुड़ी शर्तें होती हैं. इनके उदाहरण हैं:

सीमा जानकारी
requires = [
   feature_set (features = [
       'feature-name-1',
       'feature-name-2'
   ]),
]
सुविधा-लेवल. यह सुविधा सिर्फ़ तब काम करती है, जब बताई गई ज़रूरी सुविधाएं चालू हों. उदाहरण के लिए, जब कोई सुविधा सिर्फ़ कुछ बिल्ड मोड (opt, dbg या fastbuild) में काम करती है. अगर `ज़रूरी है` में एक से ज़्यादा `feature_set`हैं, तो यह सुविधा तब काम करती है, जब कोई भी `feature_set`काम करता है (जब सभी सुविधाएं चालू हों).
implies = ['feature']

सुविधा-लेवल. यह सुविधा, बताई गई सुविधा(सुविधाओं) को शामिल करती है. किसी सुविधा को चालू करने पर, उसमें शामिल सभी सुविधाएं भी अपने-आप चालू हो जाती हैं. इसका मतलब है कि यह बार-बार काम करती है.

सैनिटाइज़र के सामान्य हिस्सों जैसे सुविधाओं के एक सेट में से कुछ सामान्य फ़ंक्शन को शामिल करने की क्षमता भी देता है. शामिल सुविधाओं को बंद नहीं किया जा सकता.

provides = ['feature']

सुविधा-लेवल. इससे पता चलता है कि यह सुविधा, उपयोगकर्ताओं के लिए उपलब्ध कई खास वैकल्पिक सुविधाओं में से एक है. उदाहरण के लिए, सभी सैनिटाइज़र, provides = ["sanitizer"] के बारे में बता सकते हैं.

अगर उपयोगकर्ता एक साथ दो या इससे ज़्यादा खास सुविधाएं मांगता है, तो विकल्पों की सूची बनाकर इससे गड़बड़ियों को मैनेज करने में मदद मिलती है.

with_features = [
  with_feature_set(
    features = ['feature-1'],
    not_features = ['feature-2'],
  ),
]
फ़्लैग सेट-लेवल. सुविधा, एक से ज़्यादा फ़्लैग सेट के बारे में बता सकती है. with_features तय होने पर, फ़्लैग सेट बिल्ड कमांड तक सिर्फ़ तब बड़ा होगा, जब कम से कम एक with_feature_set हो, जिसके लिए बताए गए features सेट की सभी सुविधाएं चालू हों और not_features सेट में बताई गई सभी सुविधाएं बंद हों. अगर with_features के बारे में नहीं बताया गया है, तो तय की गई हर कार्रवाई के लिए, फ़्लैग सेट को बिना किसी शर्त के लागू किया जाएगा.

कार्रवाइयां

कार्रवाइयों से, उन परिस्थितियों में बदलाव करने की सुविधा मिलती है जिनमें कार्रवाई पूरी होती है. हालांकि, यह उम्मीद नहीं की जाती कि कार्रवाई कैसे होगी. action_config, किसी कार्रवाई को शुरू करने वाली टूल बाइनरी के बारे में बताता है. वहीं, feature कॉन्फ़िगरेशन (फ़्लैग) के बारे में बताता है, जो यह तय करता है कि कार्रवाई शुरू होने पर वह टूल कैसे काम करता है.

सुविधाएँ यह बताने के लिए कार्रवाइयों का रेफ़रंस देती हैं कि Basel की किन कार्रवाइयों पर असर पड़ता है, क्योंकि कार्रवाइयाँ बेज़ल ऐक्शन ग्राफ़ में बदलाव कर सकती हैं. CcToolchainConfigInfo सेवा देने वाली कंपनी में ऐसी कार्रवाइयां होती हैं जिनमें उससे जुड़े फ़्लैग और टूल होते हैं, जैसे कि c++-compile. हर कार्रवाई के लिए फ़्लैग असाइन किए जाते हैं. इसके लिए, उन्हें किसी सुविधा से जोड़ा जाता है.

हर कार्रवाई के नाम से, एक ही तरह की कार्रवाई के बारे में पता चलता है, जैसे कि कंपाइल करना या लिंक करना. हालांकि, ऐक्शन और बेज़ल ऐक्शन टाइप के बीच कई चीज़ें एक जैसी होती हैं, जहां बेज़ल ऐक्शन टाइप, कार्रवाई को लागू करने वाली Java क्लास (जैसे, CppCompileAction) होता है. खास तौर पर, इस टेबल में "असेंबलर ऐक्शन" और "कंपाइलर ऐक्शन" CppCompileAction हैं, जबकि लिंक ऐक्शन CppLinkAction हैं.

असेंबलर की कार्रवाइयां

कार्रवाई जानकारी
preprocess-assemble प्री-प्रोसेसिंग की मदद से असेंबल करें. आम तौर पर, .S फ़ाइलों के लिए.
assemble प्री-प्रोसेसिंग के बिना असेंबल करें. आम तौर पर, .s फ़ाइलों के लिए.

कंपाइलर की कार्रवाइयां

कार्रवाई जानकारी
cc-flags-make-variable CC_FLAGS को जेन रूल में लागू करता है.
c-compile सी॰ के तौर पर कंपाइल करें
c++-compile C++ के तौर पर कंपाइल करें.
c++-header-parsing हेडर फ़ाइल पर कंपाइलर का पार्सर चलाएं, ताकि यह पक्का किया जा सके कि हेडर अपने-आप शामिल हो. ऐसा नहीं करने पर, कंपाइलर के साथ गड़बड़ियां पैदा होंगी. यह सिर्फ़ उन टूलचेन पर लागू होता है जो मॉड्यूल के साथ काम करते हैं.
कार्रवाई जानकारी
c++-link-dynamic-library एक शेयर की गई लाइब्रेरी को लिंक करें जिसमें उसकी सभी डिपेंडेंसी शामिल हों.
c++-link-nodeps-dynamic-library सिर्फ़ cc_library स्रोतों वाली शेयर लाइब्रेरी लिंक करें.
c++-link-executable चलाने के लिए तैयार आखिरी लाइब्रेरी लिंक करें.

एआर से जुड़ी कार्रवाइयां

एआर कार्रवाइयां, ऑब्जेक्ट फ़ाइलों को ar के ज़रिए संग्रह वाली लाइब्रेरी (.a फ़ाइलें) में जोड़ती हैं. साथ ही, कुछ सिमेंटिक को नाम में कोड में बदल देती हैं.

कार्रवाई जानकारी
c++-link-static-library स्टैटिक लाइब्रेरी (संग्रह) बनाएं.

एलटीओ की कार्रवाइयां

कार्रवाई जानकारी
lto-backend बिटकोड को नेटिव ऑब्जेक्ट में कंपाइल करने वाली थिनएलटीओ कार्रवाई.
lto-index थिनएलटीओ ऐक्शन, ग्लोबल इंडेक्स जनरेट कर रहा है.

action_config का इस्तेमाल किया जा रहा है

action_config एक Starlark स्ट्रक्चर है. यह बेज़ल ऐक्शन के बारे में बताता है. इसके लिए, कार्रवाई और सुविधाओं के हिसाब से फ़्लैग के सेट को शुरू करने के लिए टूल (बाइनरी) की जानकारी दी जाती है. ये फ़्लैग, कार्रवाई के पूरा होने पर पाबंदियां लागू करते हैं.

action_config() कंस्ट्रक्टर में ये पैरामीटर हैं:

एट्रिब्यूट जानकारी
action_name यह कार्रवाई जिससे गेम को खास तौर पर अपडेट किया गया है. बेज़ल इस एट्रिब्यूट का इस्तेमाल, हर कार्रवाई के लिए टूल और इसे लागू करने से जुड़ी ज़रूरी शर्तों के बारे में जानने के लिए करते हैं.
tools यह कोड एक्ज़ीक्यूट करने के लिए इस्तेमाल किया जाता है. कार्रवाई पर लागू किया गया टूल, सूची का पहला टूल होगा. इसमें सुविधाओं के ऐसे सेट होंगे जो सुविधा के कॉन्फ़िगरेशन से मेल खाते होंगे. डिफ़ॉल्ट मान देना ज़रूरी है.
flag_sets कई कार्रवाइयों पर लागू होने वाले फ़्लैग की सूची. यह सुविधा, दोनों सुविधाओं के लिए लागू होती है.
env_sets एनवायरमेंट कंस्ट्रेंट की एक सूची, जो कार्रवाइयों के एक ग्रुप पर लागू होती है. यह सुविधा के लिए लागू होती है.

action_config के लिए दूसरी सुविधाओं और action_config की ज़रूरत हो सकती है और उन्हें लागू करने के लिए, ऊपर बताए गए सुविधा के संबंधों के हिसाब से इनका इस्तेमाल भी किया जा सकता है. इस तरह का व्यवहार किसी सुविधा के जैसा ही है.

आखिरी दो एट्रिब्यूट, सुविधाओं पर उनसे जुड़े एट्रिब्यूट के हिसाब से काम के नहीं हैं. इन्हें शामिल किया गया है. ऐसा इसलिए किया गया है, क्योंकि कुछ Basel कार्रवाइयों के लिए कुछ फ़्लैग या एनवायरमेंट वैरिएबल की ज़रूरत होती है. इसका मकसद, ग़ैर-ज़रूरी action_config+feature पेयर से बचना है. आम तौर पर, एक ही सुविधा को एक से ज़्यादा action_config के साथ शेयर करना बेहतर होता है.

एक ही टूलचेन में, एक action_name के साथ एक से ज़्यादा action_config तय नहीं किए जा सकते. यह टूल पाथ में अस्पष्टता को रोकता है और action_config के मकसद को लागू करता है - कि टूलचेन में किसी कार्रवाई की प्रॉपर्टी के बारे में एक ही जगह पर साफ़ तौर पर बताया गया है.

टूल कंस्ट्रक्टर का इस्तेमाल करना

action_config अपने tools पैरामीटर की मदद से, टूल का एक सेट तय कर सकता है. tool() कंस्ट्रक्टर, ये पैरामीटर इस्तेमाल करता है:

फ़ील्ड जानकारी
path उस टूल का पाथ जिस पर दावा किया गया है (मौजूदा जगह के हिसाब से).
with_features सुविधा के सेट की एक सूची. इस सूची में से किसी एक को पूरा करने के बाद ही इस टूल का इस्तेमाल किया जा सकता है.

किसी दिए गए action_config के लिए, सिर्फ़ एक tool इसके टूल पाथ और बेज़ेल ऐक्शन पर लागू करने की ज़रूरी शर्तों को लागू करता है. किसी टूल को action_config पर tools एट्रिब्यूट की मदद से तब तक चुना जाता है, जब तक कि सुविधा के कॉन्फ़िगरेशन से मेल खाने वाला with_feature सेट नहीं मिल जाता. (ज़्यादा जानकारी के लिए, इस पेज पर पहले सुविधा के बीच संबंध देखें. आपको अपनी टूल सूचियों के अंत में एक ऐसे डिफ़ॉल्ट टूल को देना चाहिए, जो किसी खाली सुविधा कॉन्फ़िगरेशन से संबंधित हो.

इस्तेमाल से जुड़ा उदाहरण

सुविधाओं और कार्रवाइयों का एक साथ इस्तेमाल करके, अलग-अलग क्रॉस-प्लैटफ़ॉर्म सिमैंटिक्स के साथ Basel की कार्रवाइयों को लागू किया जा सकता है. उदाहरण के लिए, macOS पर डीबग सिंबल जनरेट करने के लिए, कंपाइल ऐक्शन में सिंबल जनरेट करने होते हैं. इसके बाद, कंप्रेस किया गया dsim संग्रह बनाने के लिए किसी खास टूल को चालू करना होता है. इसके बाद, Xcode के ज़रिए इस्तेमाल किए जा सकने वाले ऐप्लिकेशन बंडल और .plist फ़ाइलें बनाने के लिए, उस संग्रह को डीकंप्रेस करना ज़रूरी होता है.

Basel के साथ, इस प्रोसेस को यहां बताए गए तरीके से लागू किया जा सकता है. unbundle-debuginfo का मतलब है, Basel का ऐक्शन:

load("@rules_cc//cc:defs.bzl", "ACTION_NAMES")

action_configs = [
    action_config (
        action_name = ACTION_NAMES.cpp_link_executable,
        tools = [
            tool(
                with_features = [
                    with_feature(features=["generate-debug-symbols"]),
                ],
                path = "toolchain/mac/ld-with-dsym-packaging",
            ),
            tool (path = "toolchain/mac/ld"),
        ],
    ),
]

features = [
    feature(
        name = "generate-debug-symbols",
        flag_sets = [
            flag_set (
                actions = [
                    ACTION_NAMES.c_compile,
                    ACTION_NAMES.cpp_compile
                ],
                flag_groups = [
                    flag_group(
                        flags = ["-g"],
                    ),
                ],
            )
        ],
        implies = ["unbundle-debuginfo"],
   ),
]

इस सुविधा को, Linux के लिए पूरी तरह से अलग तरीके से लागू किया जा सकता है. Linux fission का इस्तेमाल करता है. इसके अलावा, Windows के लिए .pdb फ़ाइलें बनाने वाले Windows के लिए भी यह सुविधा अलग-अलग तरीके से लागू की जा सकती है. उदाहरण के लिए, fission पर आधारित डीबग सिंबल जनरेट करने का तरीका ऐसा दिख सकता है:

load("@rules_cc//cc:defs.bzl", "ACTION_NAMES")

action_configs = [
    action_config (
        name = ACTION_NAMES.cpp_compile,
        tools = [
            tool(
                path = "toolchain/bin/gcc",
            ),
        ],
    ),
]

features = [
    feature (
        name = "generate-debug-symbols",
        requires = [with_feature_set(features = ["dbg"])],
        flag_sets = [
            flag_set(
                actions = [ACTION_NAMES.cpp_compile],
                flag_groups = [
                    flag_group(
                        flags = ["-gsplit-dwarf"],
                    ),
                ],
            ),
            flag_set(
                actions = [ACTION_NAMES.cpp_link_executable],
                flag_groups = [
                    flag_group(
                        flags = ["-Wl", "--gdb-index"],
                    ),
                ],
            ),
      ],
    ),
]

फ़्लैग ग्रुप

CcToolchainConfigInfo की मदद से, फ़्लैग को ऐसे ग्रुप में बंडल किया जा सकता है जो खास मकसद को पूरा करते हैं. आपके पास फ़्लैग वैल्यू में पहले से तय वैरिएबल का इस्तेमाल करके फ़्लैग तय करने का विकल्प होता है. इसे बिल्ड कमांड में फ़्लैग जोड़ते समय कंपाइलर बड़ा कर देता है. उदाहरण के लिए:

flag_group (
    flags = ["%{output_execpath}"],
)

ऐसे मामले में, फ़्लैग के कॉन्टेंट को कार्रवाई के आउटपुट फ़ाइल पाथ से बदल दिया जाएगा.

फ़्लैग ग्रुप, बिल्ड कमांड तक उस क्रम में बढ़ाए जाते हैं जिस क्रम में वे सूची में ऊपर से नीचे, बाएं से दाएं दिखते हैं.

जिन फ़्लैग को बिल्ड कमांड में जोड़े जाने पर अलग-अलग वैल्यू के साथ दोहराना होता है उनके लिए, फ़्लैग ग्रुप list टाइप के वैरिएबल को दोहरा सकता है. उदाहरण के लिए, list टाइप का वैरिएबल include_path:

flag_group (
    iterate_over = "include_paths",
    flags = ["-I%{include_paths}"],
)

include_paths सूची में हर पाथ एलिमेंट के लिए, -I<path> तक बड़ा होता है. फ़्लैग ग्रुप की जानकारी के मुख्य हिस्से में मौजूद सभी फ़्लैग (या flag_group) को एक यूनिट के तौर पर बड़ा किया जाता है. उदाहरण के लिए:

flag_group (
    iterate_over = "include_paths",
    flags = ["-I", "%{include_paths}"],
)

include_paths सूची में हर पाथ एलिमेंट के लिए, -I <path> तक बड़ा होता है.

किसी वैरिएबल को कई बार दोहराया जा सकता है. उदाहरण के लिए:

flag_group (
    iterate_over = "include_paths",
    flags = ["-iprefix=%{include_paths}", "-isystem=%{include_paths}"],
)

इसमें बड़ा होगा:

-iprefix=<inc0> -isystem=<inc0> -iprefix=<inc1> -isystem=<inc1>

वैरिएबल, डॉट-नोटेशन का इस्तेमाल करके ऐक्सेस किए जा सकने वाले स्ट्रक्चर के मुताबिक हो सकते हैं. जैसे:

flag_group (
    flags = ["-l%{libraries_to_link.name}"],
)

स्ट्रक्चर को नेस्ट किया जा सकता है और इनमें क्रम भी हो सकते हैं. नाम के बीच टकराव रोकने और साफ़ तौर पर साफ़ तौर पर नाम बताने के लिए, आपको फ़ील्ड में पूरा पाथ बताना होगा. जैसे:

flag_group (
    iterate_over = "libraries_to_link",
    flag_groups = [
        flag_group (
            iterate_over = "libraries_to_link.shared_libraries",
            flags = ["-l%{libraries_to_link.shared_libraries.name}"],
        ),
    ],
)

शर्तों के साथ बड़ा करना

फ़्लैग ग्रुप में, किसी खास वैरिएबल या उसके फ़ील्ड की मौजूदगी के आधार पर, उसका दायरा बढ़ाया जा सकता है. इसके लिए, expand_if_available, expand_if_not_available, expand_if_true, expand_if_false या expand_if_equal एट्रिब्यूट का इस्तेमाल किया जाता है. उदाहरण के लिए:

flag_group (
    iterate_over = "libraries_to_link",
    flag_groups = [
        flag_group (
            iterate_over = "libraries_to_link.shared_libraries",
            flag_groups = [
                flag_group (
                    expand_if_available = "libraries_to_link.shared_libraries.is_whole_archive",
                    flags = ["--whole_archive"],
                ),
                flag_group (
                    flags = ["-l%{libraries_to_link.shared_libraries.name}"],
                ),
                flag_group (
                    expand_if_available = "libraries_to_link.shared_libraries.is_whole_archive",
                    flags = ["--no_whole_archive"],
                ),
            ],
        ),
    ],
)

CcToolchainConfigInfo का रेफ़रंस

इस सेक्शन में बिल्ड वैरिएबल, सुविधाओं, और C++ के नियमों को कॉन्फ़िगर करने के लिए ज़रूरी अन्य जानकारी के बारे में बताया गया है.

CcToolchainConfigInfo बिल्ड वैरिएबल

यहां CcToolchainConfigInfo बिल्ड वैरिएबल का रेफ़रंस दिया गया है.

वैरिएबल कार्रवाई जानकारी
source_file compile कंपाइल की जाने वाली सोर्स फ़ाइल.
input_file स्ट्रिप हटाने के लिए आर्टफ़ैक्ट.
output_file कंपाइल, स्ट्रिप कंपाइलेशन आउटपुट.
output_assembly_file compile उत्सर्जित असेंबली फ़ाइल. यह सिर्फ़ तब लागू होता है, जब compile ऐक्शन से असेंबली टेक्स्ट निकलता है. आम तौर पर, ऐसा तब होता है, जब --save_temps फ़्लैग का इस्तेमाल किया जाता है. output_file में मौजूद कॉन्टेंट एक जैसा है.
output_preprocess_file compile पहले से प्रोसेस किया गया आउटपुट. सिर्फ़ उन कार्रवाइयों को इकट्ठा करने पर लागू होती है जो सिर्फ़ सोर्स फ़ाइलों को पहले से प्रोसेस करती हैं. आम तौर पर, ऐसा तब होता है, जब --save_temps फ़्लैग का इस्तेमाल किया जा रहा हो. output_file में मौजूद कॉन्टेंट एक जैसा है.
includes compile फ़ाइलों का क्रम, जो कंपाइलर को कंपाइल किए गए सोर्स में बिना किसी शर्त के शामिल करना चाहिए.
include_paths compile क्रम वाली डायरेक्ट्री, जिनमें कंपाइलर #include<foo.h> और #include "foo.h" का इस्तेमाल करके, शामिल हेडर खोजता है.
quote_include_paths compile -iquote के क्रम में - वे डायरेक्ट्री शामिल होती हैं जिनमें कंपाइलर #include "foo.h" का इस्तेमाल करके, हेडर खोजता है.
system_include_paths compile -isystem के क्रम में - वे डायरेक्ट्री शामिल होती हैं जिनमें कंपाइलर #include <foo.h> का इस्तेमाल करके, हेडर खोजता है.
dependency_file compile कंपाइलर से जनरेट की गई .d डिपेंडेंसी फ़ाइल.
preprocessor_defines compile defines का क्रम, जैसे कि --DDEBUG.
pic compile आउटपुट को पोज़िशन-इंडिपेंडेंट कोड के तौर पर कंपाइल करता है.
gcov_gcno_file compile gcov कवरेज फ़ाइल.
per_object_debug_info_file compile हर ऑब्जेक्ट की डीबग की जानकारी (.dwp) फ़ाइल.
stripotps स्ट्रिप stripopts का क्रम.
legacy_compile_flags compile compiler_flag, optional_compiler_flag, cxx_flag, और optional_cxx_flag जैसे लेगसी CROSSTOOL फ़ील्ड से मिले फ़्लैग का क्रम.
user_compile_flags compile copt नियम एट्रिब्यूट या --copt, --cxxopt, और --conlyopt फ़्लैग से फ़्लैग का क्रम.
unfiltered_compile_flags compile unfiltered_cxx_flag के लेगसी CROSSTOOL फ़ील्ड या unfiltered_compile_flags सुविधा से मिले फ़्लैग का क्रम. इन्हें nocopts नियम एट्रिब्यूट के हिसाब से फ़िल्टर नहीं किया जाता.
sysroot sysroot.
runtime_library_search_directories लिंक लिंकर रनटाइम खोज पाथ में एंट्री (आम तौर पर -rpath फ़्लैग के साथ सेट की जाती हैं).
library_search_directories लिंक लिंकर के खोज पाथ में एंट्री (आम तौर पर, -L फ़्लैग के साथ सेट की जाती है).
libraries_to_link लिंक लिंक करने वाले मैसेज में इनपुट के तौर पर लिंक करने के लिए फ़ाइलें उपलब्ध कराने वाले फ़्लैग.
def_file_path लिंक Windows पर MSVC के साथ इस्तेमाल की गई def फ़ाइल की जगह.
linker_param_file लिंक कमांड लाइन की लंबाई की सीमा पार करने के लिए, बैजर की ओर से बनाई गई लिंकर पैरामीटर फ़ाइल की जगह की जानकारी.
output_execpath लिंक लिंकर के आउटपुट का एक्ज़ीकपैट.
generate_interface_library लिंक "yes" या "no" इस बात पर निर्भर करता है कि इंटरफ़ेस लाइब्रेरी जनरेट करनी है या नहीं.
interface_library_builder_path लिंक इंटरफ़ेस लाइब्रेरी बिल्डर टूल का पाथ.
interface_library_input_path लिंक इंटरफ़ेस लाइब्रेरी ifso बिल्डर टूल के लिए इनपुट.
interface_library_output_path लिंक ifso बिल्डर टूल का इस्तेमाल करके, इंटरफ़ेस लाइब्रेरी जनरेट करने के लिए पाथ.
legacy_link_flags लिंक CROSSTOOL के लेगसी फ़ील्ड से मिलने वाले लिंकर फ़्लैग.
user_link_flags लिंक --linkopt या linkopts एट्रिब्यूट से मिलने वाले लिंकर फ़्लैग.
linkstamp_paths लिंक लिंकस्टैंप पाथ देने वाला बिल्ड वैरिएबल.
force_pic लिंक इस वैरिएबल के मौजूद होने से यह पता चलता है कि PIC/PIE कोड जनरेट करना ज़रूरी है (Baज़ल विकल्प `--force_pic` पास किया गया था).
strip_debug_symbols लिंक इस वैरिएबल के मौजूद होने का मतलब है कि डीबग सिंबल हटा दिए जाने चाहिए.
is_cc_test लिंक सही है, जब मौजूदा कार्रवाई cc_test लिंक करने की कार्रवाई है, नहीं तो गलत.
is_using_fission कंपाइल, लिंक इस वैरिएबल के मौजूद होने से पता चलता है कि फ़िज़न (हर ऑब्जेक्ट के लिए डीबग की जानकारी) चालू है. डीबग की जानकारी, .o फ़ाइलों के बजाय .dwo फ़ाइलों में होगी. साथ ही, कंपाइलर और लिंकर को यह जानने की ज़रूरत होगी.
fdo_instrument_path कंपाइल, लिंक उस डायरेक्ट्री का पाथ जिसमें एफ़डीओ की इंस्ट्रुमेंटेशन प्रोफ़ाइल सेव की जाती है.
fdo_profile_path compile एफ़डीओ प्रोफ़ाइल का पाथ.
fdo_prefetch_hints_path compile कैश मेमोरी प्रीफ़ेच प्रोफ़ाइल का पाथ.
cs_fdo_instrument_path कंपाइल, लिंक उस डायरेक्ट्री का पाथ जिसमें कॉन्टेक्स्ट के हिसाब से एफ़डीओ इंस्ट्रुमेंटेशन प्रोफ़ाइल को सेव किया जाता है.

लोकप्रिय सुविधाएं

सुविधाओं और उन्हें चालू करने की शर्तों की जानकारी नीचे दी गई है.

सुविधा दस्तावेज़ के रूप में
opt | dbg | fastbuild यह सुविधा, कंपाइलेशन मोड के आधार पर डिफ़ॉल्ट रूप से चालू होती है.
static_linking_mode | dynamic_linking_mode यह सुविधा, लिंकिंग मोड के आधार पर डिफ़ॉल्ट रूप से चालू होती है.
per_object_debug_info यह तब चालू होता है, जब supports_fission सुविधा के बारे में बताया गया हो और उसे चालू किया गया हो. साथ ही, --fission फ़्लैग में मौजूदा कंपाइलेशन मोड की जानकारी भी दी गई हो.
supports_start_end_lib अगर यह नीति चालू है (और --start_end_lib विकल्प सेट है), तो Basel का विकल्प स्टैटिक लाइब्रेरी से लिंक नहीं होगा. इसके बजाय, वह सीधे ऑब्जेक्ट से लिंक करने के लिए, --start-lib/--end-lib लिंकर के विकल्पों का इस्तेमाल करेगा. इससे बिल्ड तेज़ी से पूरा होता है, क्योंकि Basel को स्टैटिक लाइब्रेरी बनाने की ज़रूरत नहीं है.
supports_interface_shared_libraries यह नीति चालू होने पर (और --interface_shared_objects विकल्प सेट है), Ba तो, उन टारगेट को लिंक करेगा जिनमें linkstatic को 'गलत है' (डिफ़ॉल्ट रूप से cc_test) पर सेट किया गया है. ऐसा, इंटरफ़ेस की शेयर की गई लाइब्रेरी से किया जा सकता है. इससे तेज़ी से फिर से लिंक किया जाता है.
supports_dynamic_linker अगर C++ के नियमों को चालू किया जाता है, तो उन्हें पता चल जाएगा कि टूलचेन, शेयर की गई लाइब्रेरी बना सकता है.
static_link_cpp_runtimes अगर यह नीति चालू की जाती है, तो Basel के C++ रनटाइम को स्टैटिक लिंकिंग मोड में और डाइनैमिक तौर पर डाइनैमिक लिंकिंग मोड में, लिंक किया जाएगा. लिंक करने के मोड के आधार पर, cc_toolchain.static_runtime_lib या cc_toolchain.dynamic_runtime_lib एट्रिब्यूट में दिए गए आर्टफ़ैक्ट, लिंक करने की कार्रवाइयों में जोड़ दिए जाएंगे.
supports_pic अगर यह सुविधा चालू है, तो टूलचेन को डाइनैमिक लाइब्रेरी के लिए PIC ऑब्जेक्ट का इस्तेमाल करने की जानकारी मिल जाएगी. जब भी पीआईसी कंपाइलेशन की ज़रूरत हो, तब `पिक` वैरिएबल मौजूद होता है. अगर यह सुविधा डिफ़ॉल्ट रूप से चालू नहीं है और `--force_pic` को पास किया जाता है, तो Ba बैंक, `supports_pic` का अनुरोध करेगा और यह पुष्टि करेगा कि यह सुविधा चालू है. अगर सुविधा मौजूद नहीं है या उसे चालू नहीं किया जा सकता, तो `--force_pic` का इस्तेमाल नहीं किया जा सकता.
static_linking_mode | dynamic_linking_mode यह सुविधा, लिंकिंग मोड के आधार पर डिफ़ॉल्ट रूप से चालू होती है.
no_legacy_features यह C++ कॉन्फ़िगरेशन के मौजूद होने पर, Basel को लेगसी सुविधाओं को C++ कॉन्फ़िगरेशन में जोड़ने से रोकता है. सुविधाओं की पूरी सूची नीचे देखें.

लेगसी सुविधाएं, लॉजिक को पैच कर रही हैं

Basel ने पिछले वर्शन के साथ काम करने के लिए, टूलचेन की सुविधाओं में ये बदलाव लागू किए हैं:

  • इस विकल्प की मदद से, legacy_compile_flags सुविधा को टूलचेन में सबसे ऊपर ले जाया जाता है
  • इस विकल्प की मदद से, default_compile_flags सुविधा को टूलचेन में सबसे ऊपर ले जाया जाता है
  • टूलचेन के सबसे ऊपर dependency_file (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर pic (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर per_object_debug_info (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर preprocessor_defines (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर includes (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर include_paths (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर fdo_instrument (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर fdo_optimize (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर cs_fdo_instrument (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर cs_fdo_optimize (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर fdo_prefetch_hints (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर autofdo (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर build_interface_libraries (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर dynamic_library_linker_tool (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर shared_flag (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर linkstamps (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर output_execpath_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर runtime_library_search_directories (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर library_search_directories (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर archiver_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर libraries_to_link (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर force_pic_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर user_link_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर legacy_link_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर static_libgcc (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर fission_support (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर strip_debug_symbols (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर coverage (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर llvm_coverage_map_format (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे ऊपर gcc_coverage_map_format (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे नीचे fully_static_link (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे नीचे user_compile_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे नीचे sysroot (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे नीचे unfiltered_compile_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे नीचे linker_param_file (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे नीचे compiler_input_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है
  • टूलचेन के सबसे नीचे compiler_output_flags (अगर मौजूद नहीं है) सुविधा जोड़ता है

यह सुविधाओं की एक लंबी सूची है. हमारी योजना है कि स्टारलार्क में क्रॉसटूल खत्म हो जाने के बाद, आपको इनसे छुटकारा मिल जाए. जानकारी पाने वाले लोगों के लिए, CppActionConfigs में लागू करने की जानकारी देखें. प्रोडक्शन टूलचेन के लिए, टूलचेन को ज़्यादा स्टैंडअलोन बनाने के लिए no_legacy_features जोड़ें.