2011-12-23 5 views
7

मैं इनलाइन असेंबली के बारे में पढ़ रहा हूं। मैं एक्सकोड 4 एलएलवीएम 3.0 कंपाइलर के तहत आईफोन में एक साधारण दिनचर्या लिखना चाहता हूं। मैं मूल इनलाइन असेंबली कोड लिखने में सफल होता हूं।एक्सकोड एलएलवीएम में लूप के बारे में इनलाइन असेंबली कोड कैसे लिखें?

उदाहरण:

int sub(int a, int b) 
{ 
    int c; 
    asm ("sub %0, %1, %2" : "=r" (c) : "r" (a), "r" (b)); 
    return c; 
} 

मैं इसमें stackoverflow.com पाया जाता है और यह बहुत अच्छी तरह से काम करता है। लेकिन, मुझे नहीं पता कि लूप के बारे में कोड कैसे लिखना है।

मैं की तरह

void brighten(unsigned char* src, unsigned char* dst, int numPixels, int intensity) 
{ 
    for(int i=0; i<numPixels; i++) 
    { 
     dst[i] = src[i] + intensity; 
    } 
} 
+2

इस तरह के कार्यों को ओपनजीएल ईएस और एक टुकड़ा शेडर का उपयोग करके भी कार्यान्वित किया जा सकता है। अगर यह आपकी समस्या पर लागू होता है। इससे आपको "मुक्त" के समानांतरता मिल जाएगी, जैसा कि मैट के सुझाव के रूप में नीयन के उपयोग के समान है। – Arne

+0

ये आप निश्चित रूप से ओपनजीएल ES का उपयोग कर सकते हैं। आप जो कर रहे हैं उस पर बहुत निर्भर करता है और यदि आप इसे निर्भरता के रूप में खींचना चाहते हैं। – mattjgalloway

+0

ओपनजीएल ईएस पर्याप्त तेज़ नहीं हो सकता है अगर उसे सीपीयू पर गणना की गई राशि वापस प्राप्त करने की आवश्यकता है। इस कार्य को कुशलता से करने के लिए आईपैड जीपीयू का निर्माण नहीं किया जाता है। – Etan

उत्तर

5

विधानसभा कोड की जरूरत है पाश अनुभाग में यहाँ एक नजर डालें - http://en.wikipedia.org/wiki/ARM_architecture

मूल रूप से आप की तरह कुछ चाहता हूँ:

void brighten(unsigned char* src, unsigned char* dst, int numPixels, int intensity) { 
    asm volatile (
        "\t mov r3, #0\n" 
        "Lloop:\n" 
        "\t cmp r3, %2\n" 
        "\t bge Lend\n" 
        "\t ldrb r4, [%0, r3]\n" 
        "\t add r4, r4, %3\n" 
        "\t strb r4, [%1, r3]\n" 
        "\t add r3, r3, #1\n" 
        "\t b Lloop\n" 
        "Lend:\n" 
       : "=r"(src), "=r"(dst), "=r"(numPixels), "=r"(intensity) 
       : "0"(src), "1"(dst), "2"(numPixels), "3"(intensity) 
       : "cc", "r3", "r4"); 
} 

अद्यतन:

एन डी यहाँ है कि NEON संस्करण:

void brighten_neon(unsigned char* src, unsigned char* dst, int numPixels, int intensity) { 
    asm volatile (
        "\t mov r4, #0\n" 
        "\t vdup.8 d1, %3\n" 
        "Lloop2:\n" 
        "\t cmp r4, %2\n" 
        "\t bge Lend2\n" 
        "\t vld1.8 d0, [%0]!\n" 
        "\t vqadd.s8 d0, d0, d1\n" 
        "\t vst1.8 d0, [%1]!\n" 
        "\t add r4, r4, #8\n" 
        "\t b Lloop2\n" 
        "Lend2:\n" 
        : "=r"(src), "=r"(dst), "=r"(numPixels), "=r"(intensity) 
        : "0"(src), "1"(dst), "2"(numPixels), "3"(intensity) 
        : "cc", "r4", "d1", "d0"); 
} 

तो यह नियॉन संस्करण एक समय में 8 करेगा। हालांकि यह जांच नहीं करता कि numPixels 8 तक विभाजित है, इसलिए आप निश्चित रूप से ऐसा करना चाहते हैं अन्यथा चीजें गलत हो जाएंगी! वैसे भी, यह आपको दिखाने के लिए एक शुरुआत है कि क्या किया जा सकता है। निर्देशों की एक ही संख्या पर ध्यान दें, लेकिन एक बार में आठ पिक्सेल डेटा पर कार्रवाई करें। ओह और यह वहां संतृप्ति भी है जैसा कि मुझे लगता है कि आप चाहते हैं।

+0

ये कोड बहुत अच्छी तरह से काम करते हैं!यह मेरी समझ के लिए वास्तव में सहायक था। आपकी सलाह के लिए बहुत बहुत धन्यवाद ~ –

-2

हालांकि यह उत्तर सीधे आपके प्रश्न का उत्तर नहीं है, यह आधुनिक कंपाइलर बनाम असेंबलर के उपयोग के संबंध में एक सामान्य सलाह है।

आपको आमतौर पर अपने सी कोड के अनुकूलन के संबंध में संकलक को मारने में कठिनाई होगी। बेशक आपके डेटा का व्यवहार करने के बारे में कुछ ज्ञान के चालाक उपयोग से यह संभव है कि आप इसे कुछ पर्सेंट ट्विक कर सकें।

इसके कारणों में से एक यह है कि आधुनिक कंपाइलर आपके द्वारा वर्णित कोड जैसे कोड से निपटने के दौरान कई तकनीकों का उपयोग करते हैं, उदाहरण के लिए लूप अनोलिंग, पाइपलाइन स्टालों और बुलबुले से बचने के लिए निर्देश पुनर्निर्देशन,

यदि आप वास्तव में उस एल्गोरिदम चिल्लाते हैं, तो आपको सी में बजाय एल्गोरिदम को फिर से डिजाइन करने पर विचार करना चाहिए ताकि आप सबसे खराब देरी से बच सकें। उदाहरण के लिए, स्मृति तक पढ़ने और लिखना पंजीकरण पहुंच की तुलना में महंगा है।

यह पूरा करने का एक तरीका यह हो सकता है कि unsigned long का उपयोग कर एक बार में अपने कोड को 4 बाइट लोड करें और फिर एक स्टोर ऑपरेशन में इन 4 बाइट्स को वापस लिखने से पहले रजिस्टरों में गणित कर रहे हों।

तो संक्षेप में, अपने एल्गोरिदम को कड़ी मेहनत से कड़ी मेहनत न करें।

+1

शायद वह सीखने में व्यायाम के रूप में ऐसा करना चाहता है? या यह सुनिश्चित करना चाहता है कि एनईओएन से वेक्टर निर्देश सही तरीके से उपयोग किए जा रहे हैं? ऐसा लगता है कि वह पिक्सेल डेटा के साथ सामान करना चाहता है और निश्चित रूप से कुछ वेक्टर निर्देशों से लाभान्वित होता है। उदाहरण के लिए, आप एक समय में 16 पिक्सेल जोड़ और संतृप्त कर सकते हैं। – mattjgalloway

+2

विशेष रूप से एआरएम पर, कंपाइलर्स अभी तक आपके द्वारा कल्पना की जाने वाली स्तर पर नहीं हैं। सिम निर्देशों के साथ-साथ बिट फील्ड ऑपरेशंस को खराब तरीके से अनुकूलित किया जाता है और आप सीधे एआरएम में कोडिंग करके बड़ी गति प्राप्त कर सकते हैं। ध्यान दें कि ऐपस्टोर केवल उन ऐप्स को स्वीकार करता है जो केवल प्रलेखित एपीआई का उपयोग करते हैं। इस बारे में निश्चित नहीं है कि इनलाइन असेंबलर ऐपस्टोर योग्यता को कैसे प्रभावित करता है। – Etan

+0

इनलाइन असेंबली ऐप स्टोर योग्यता को किसी भी तरह प्रभावित नहीं करती है। वह एक अनियंत्रित एपीआई का उपयोग नहीं कर रहा है। इनलाइन असेंबली कंपाइलर/असेंबलर का एक फ़ंक्शन है इसलिए फ्रेमवर्क 'एपीआई के साथ इसका कोई लेना-देना नहीं है। – mattjgalloway

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