संकलक सीधे एलएसआर का उपयोग क्यों नहीं करता है


10

नमस्ते मैं एक Arduino Uno (इसलिए ATmega328p) का उपयोग कर एक परियोजना पर काम कर रहा हूं, जहां समय काफी महत्वपूर्ण है और इसलिए मैं यह देखना चाहता था कि संकलक मेरे कोड को किस निर्देशों में परिवर्तित कर रहा था। और वहाँ मैं एक है uint8_tजो मैं का उपयोग कर प्रत्येक पुनरावृत्ति पर दाईं ओर एक बिट स्थानांतरित कर देता हूं data >>= 1और ऐसा लगता है कि संकलक ने इसे 5 निर्देशों में अनुवादित किया है ( dataमें है r24):

mov     r18, r24
ldi     r19, 0x00
asr     r19
ror     r18
mov     r24, r18

लेकिन अगर मैं निर्देश सेट प्रलेखन में देखता हूं तो मुझे एक निर्देश दिखाई देता है जो वास्तव में ऐसा करता है: lsr r24

क्या मैं कुछ अनदेखा करता हूं या संकलक इस का उपयोग क्यों नहीं कर रहा है? रजिस्टरों r18और r19कहीं और उपयोग नहीं किया जाता है।

मैं एक आर्दूनियो का उपयोग कर रहा हूं लेकिन अगर मैं सही हूं तो यह सामान्य avr-gccकंपाइलर का उपयोग करता है । यह कोड (छंटनी) है जो अनुक्रम उत्पन्न करता है:

ISR(PCINT0_vect) {
    uint8_t data = 0;
    for (uint8_t i = 8; i > 0; --i) {
//        asm volatile ("lsr %0": "+w" (data));
        data >>= 1;
        if (PINB & (1 << PB0))
            data |= 0x80;
    }
    host_data = data;
}

जहां तक ​​मैं देख सकता हूं कि अर्दीनिनो आईडीई सिस्टम द्वारा प्रदान की गई AVR gcc कंपाइलर का उपयोग कर रहा है जो कि संस्करण 6.2.0-1.fc24 है। दोनों पैकेज मैनर के माध्यम से स्थापित किए गए हैं इसलिए अद्यतित होना चाहिए।


1
विधानसभा सी कोड के अनुरूप नहीं लगती है।
यूजीन श।

वैसे मैंने इसे आर्दूनियो आईडीई का उपयोग करके संकलित किया है और फिर avr-objdumpयोगिनी फ़ाइल पर उपयोग किया है ... यह क्या है जो मेल नहीं खाता है?
xZise

1
@Eugene श्री .: यह करता है सी कोड के अनुरूप हैं। यह सिर्फ लाइन से मेल खाती हैdata >>= 1;
दही

1
यह उन मामलों में से एक है जहां "विभाजन के बजाय पाली का उपयोग करें" गलत सलाह है। यदि आप / = 2 के बजाय संकलक lsr r24 उत्पन्न करेगा; (टिप:
gm

क्या संकलक? क्या प्रोसेसर है? यह वास्तव में स्पष्ट होना चाहिए कि सवाल बनाने के लिए यह आवश्यक जानकारी है।
ओलिन लेथ्रोप

जवाबों:


18

सी भाषा विनिर्देश के अनुसार किसी भी मूल्य जिसका आकार int(विशेष संकलक पर निर्भर करता है , के आकार से कम है, आपके मामले intमें 16-बिट्स चौड़ा है) किसी भी ऑपरेशन में शामिल है (आपके मामले में >>) intऑपरेशन से पहले ऊपर है।
कंपाइलर के इस व्यवहार को पूर्णांक संवर्धन कहा जाता है ।

और ठीक यही कंपाइलर ने किया:

  • r19 = 0 पूर्णांक के पदोन्नत मूल्य का MSByte है data
  • (r19, r18) उस के कुल पूर्णांक पदोन्नत मूल्य का प्रतिनिधित्व करता dataहै और फिर एक बिट द्वारा सही स्थानांतरित किया जाता है asr r19और ror 18
  • इसके बाद परिणाम को आपके uint8_tचर पर वापस ला दिया जाता है data:
    mov r24, r18यानी r19 में MSByte को फेंक दिया जाता है।

संपादित करें:
बेशक कंप्लीट कोड का अनुकूलन कर सकता है
समस्या को पुन: उत्पन्न करने की कोशिश कर रहा हूं कि कम से कम avr-gcc संस्करण 4.9.2 के साथ समस्या नहीं होती है। यह बहुत ही कुशल कोड बनाता है, यानी सी-लाइन data >>= 1;सिर्फ एक lsr r24निर्देश के लिए संकलित हो जाता है । तो शायद आप एक बहुत पुराने संकलक संस्करण का उपयोग कर रहे हैं।


2
यह कुल बेकार नहीं है क्योंकि कभी-कभी आपको कोडांतरक स्तर पर डिबगिंग के लिए अडॉप्ट किए गए कोड की आवश्यकता होती है। यदि आपके पास कोड नहीं है तो आप बहुत खुश हैं।
दही

3
अगर मुझे सही ढंग से याद है -mint8, पूर्णांक 8-बिट बनाने के लिए ध्वज है। हालाँकि इसके बहुत से अवांछित दुष्प्रभाव हैं। क्षमा करें, यह याद नहीं कर सकते कि वे अब क्या थे, लेकिन मैंने कभी उनके कारण ध्वज का उपयोग नहीं किया। मैंने कई साल पहले कॉमर्शियल कंपाइलर के साथ avr-gcc की तुलना में काफी समय बिताया।
जॉन

1
ओह यह सही है, सी मानक के लिए पूर्णांकों की आवश्यकता कम से कम 16-बिट है, इसलिए -mint8 का उपयोग करने से सभी लाइब्रेरीज़ टूट जाती हैं।
जॉन

9
निगेल जोन्स ने "8-बिट माइक्रोकंट्रोलर के लिए कुशल सी कोड" में कुछ इस तरह से कहा: "... सी के पूर्णांक पदोन्नति नियम संभवतः उन सबसे जघन्य अपराध हैं जो हमारे खिलाफ 8-बिट दुनिया में श्रम करते हैं" ...
डिरेसी रोड्रिग्स जूनियर

1
@ जोनास विलेकी: समस्या का सबसे अच्छा समाधान एक बेहतर संकलक का उपयोग करना है। उदाहरण के लिए avr-gcc संस्करण 4.9.2 के साथ मैं समस्या को पुन: उत्पन्न नहीं कर सकता: C कोड लाइन के लिए d >>= 1;मुझे केवल एक lsr r24निर्देश प्राप्त होता है। शायद xZise एक बहुत पुराने संकलक संस्करण का उपयोग कर रहा है।
दही
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.