2012-01-17 14 views
9

मैं वर्तमान में एसटीएम 32 मंच पर एम्बेडेड सी ++ विकास शामिल हूं। हमारी टीम विभिन्न निम्न-स्तरीय हार्डवेयर उपकरणों के लिए पैरामीट्रिज़ ड्राइवरों को टेम्पलेट्स के उपयोग का मूल्यांकन कर रही है।अप्रयुक्त टेम्पलेट इंस्टेंटेशन के स्थिर सदस्यों को हटाने

सभी वैध टेम्पलेट विशेषज्ञताएं पहले से ही जानी जाती हैं, इस प्रकार हम सभी वैध विशेषज्ञता को कार्यान्वयन फ़ाइल (कार्यान्वयन और घोषणा अलग) के अंदर स्पष्ट रूप से दे सकते हैं। असल में, हमारे लिए स्पष्ट विशेषज्ञता काफी उपयोगी है क्योंकि यह व्यवहार्य पैरामीटर सेट दस्तावेज करने में मदद करता है।

// file i2c_dev.h 

template<typename traits> 
struct i2c_dev 
{ 
public: 
    static void init(); 
    static void send(); 
    static bool busy(); 
    ... 
private: 
    static i2c_transfer periodic_transfer; // class with used-defined constructor 
}; 

// traits class for configuration A 
struct i2c_dev_traitsA 
{ 
    enum 
    { 
     I2Cx_BASE = I2C1_BASE 
    , PORTx_BASE = GPIOB_BASE 
    , PORTx_PIN_TX = PB08 
    , PORTx_PIN_RX = PB09 
    }; 
}; 

// traits class for configuration B, different I2C peripherial and pinout 
struct i2c_dev_traitsB 
{ 
    enum 
    { 
     I2Cx_BASE = I2C2_BASE 
    , PORTx_BASE = GPIOA_BASE 
    , PORTx_PIN_TX = PA01 
    , PORTx_PIN_RX = PA02 
    }; 
}; 

// file i2c_dev.cpp 

// Implementation of template functions 
template<typename traits> 
void i2c_devy<traits>::init() { ... } 

... 

// explcitly specialize for all valid traits classes 
template class i2c_dev<i2c_dev_traitsA>; 
template class i2c_dev<i2c_dev_traitsB>; 

हालांकि आम तौर पर केवल विशेषज्ञताओं में से एक वास्तव में इस्तेमाल किया जाएगा, अप्रयुक्त विशेषज्ञताओं लिए बनाए गए कोड लिंकर है, जो वास्तव में हम क्या चाहते है द्वारा अंतिम छवि से निकाल दिया जाएगा।

हालांकि, उपरोक्त नमूने में स्थिर सदस्य चर - periodic_transfer - प्रत्येक टेम्पलेट विशेषज्ञता के निष्पादन योग्य में रहते हैं, जैसा कि arm-none-eabi-nm उपकरण द्वारा उत्पन्न स्मृति मानचित्र में देखा जा सकता है। यह शायद इस तथ्य के कारण है कि i2c_transfer एक पीओडी नहीं है लेकिन उपयोगकर्ता द्वारा परिभाषित कन्स्ट्रक्टर है। जब निर्माता को हटा दिया जाता है, तो चीज़ को पीओडी प्रकार में बदलना, स्थिर सदस्य भी गायब हो जाते हैं।

स्पष्ट रूप से तत्काल, लेकिन अप्रयुक्त टेम्पलेट्स के स्थैतिक गैर-पीओडी सदस्यों को हटाने का कोई तरीका है?

सादर, आर्नी

# 1 संपादित करें: समस्या पुनर्विचार करने के बाद मैं निम्नलिखित समाधान है, जो जाहिरा तौर पर समस्या का समाधान होता के साथ आया था।

जब वर्ग i2c_transfer जो वास्तव में यह केवल स्पष्टता और उपयोग में आसानी के लिए कंस्ट्रक्टर्स है है, अपने डेटा के सदस्यों को इस तरह एक पॉड आधार वर्ग i2c_transfer_pod में चले गए हैं:

struct i2c_transfer_pod 
{ 
protected: 
    uint16_t m_size; 
    char* m_buffer; 
}; 

struct i2c_transfer : public i2c_transfer_pod 
{ 
public: 
    i2c_transfer(); 
    i2c_transfer(i2c_direction_enum dir, char*buffer, uint16_t count); 

    bool failed(); 
    bool succeeded(); 
}; 
फिर

, के अप्रयुक्त i2c_dev<traits> स्थिर सदस्यों अंतिम निष्पादन योग्य (जैसे नक्शा फ़ाइल सुझाता है) से विशेषज्ञता भी हटा दी जाती है।

संपादित करें # 2: हालांकि एक-आत्म का जवाब थोड़ा लंगड़ा लगता है .. मैं कृपया प्रस्तावित समाधान पर टिप्पणियों का अनुरोध करता हूं। क्या संभवतः एक और अधिक सुरुचिपूर्ण तरीका है? क्या संकलक वास्तव में (जैसा कि मुझे लगता है) अतिरिक्त व्युत्पन्न को अनुकूलित करने वाला है?

संपादित करें # 3: समाधान के बाद से मैं सवाल बंद करता हूं क्योंकि समाधान मेरे लिए काम करता है। मनाए गए व्यवहार के कारण में गहरी अंतर्दृष्टि रखना अच्छा लगेगा।

प्रश्न में संकलक arm-none-eabi-gcc (Sourcery G++ Lite 2011.03-42) 4.5.2

+1

यदि आपको अपनी समस्या का समाधान मिला है, तो आपको इसे एक उत्तर के रूप में पोस्ट करना चाहिए। –

+1

एक अजीब कंपाइलर टिक की तरह लगता है, क्योंकि वास्तव में वास्तव में कोई अंतर नहीं होना चाहिए, imho। – Xeo

+0

क्या लंगड़ा संकलक है, और क्या संस्करण? –

उत्तर

2

जवाब है (से संपादित करें # 1): समस्या पुनर्विचार करने के बाद मैं निम्नलिखित समाधान है, जो जाहिरा तौर पर समस्या का समाधान होता साथ आया था।

जब वर्ग i2c_transfer जो वास्तव में यह केवल स्पष्टता और उपयोग में आसानी के लिए कंस्ट्रक्टर्स है है, अपने डेटा के सदस्यों को इस तरह एक पॉड आधार वर्ग i2c_transfer_pod में चले गए हैं:

struct i2c_transfer_pod 
{ 
protected: 
    uint16_t m_size; 
    char* m_buffer; 
}; 

struct i2c_transfer : public i2c_transfer_pod 
{ 
public: 
    i2c_transfer(); 
    i2c_transfer(i2c_direction_enum dir, char*buffer, uint16_t count); 

    bool failed(); 
    bool succeeded(); 
}; 
फिर

, के अप्रयुक्त i2c_dev<traits> स्थिर सदस्यों अंतिम निष्पादन योग्य (जैसे नक्शा फ़ाइल सुझाता है) से विशेषज्ञता भी हटा दी जाती है।

संबंधित मुद्दे