سؤال

حصلت على هذه القطعة من كود التجميع المستخرجة من بعض البرامج، ولكن لسوء الحظ، لا أعرف أي شيء من المجمع والبارات التي لمستها من المجمع عادت في كومودور أميجا مع 68000.

هل يمكن لأي شخص أن يرشدني كيف يمكنني فهم هذا الرمز بدون لي بحاجة إلى تعلم المجمع من الصفر أو فقط أخبرني ماذا يفعل؟

هل هناك أي نوع من "محاكاة" هناك أنه يمكنني تشغيل هذا لمعرفة ما يفعله؟

   -[ObjSample Param1:andParam2:]:
    00000c79    pushl   %ebp
    00000c7a    movl    %esp,%ebp
    00000c7c    subl    $0x48,%esp
    00000c7f    movl    %ebx,0xf4(%ebp)
    00000c82    movl    %esi,0xf8(%ebp)
    00000c85    movl    %edi,0xfc(%ebp)
    00000c88    calll   0x00000c8d
    00000c8d    popl    %ebx
    00000c8e    cmpb    $-[ObjSample delegate],_bDoOnce.26952-0xc8d(%ebx)
    00000c95    jel 0x00000d47
    00000c9b    movb    $-[ObjSample delegate],_bDoOnce.26952-0xc8d(%ebx)
    00000ca2    movl    0x7dc0-0xc8d(%ebx),%eax
    00000ca8    movl    %eax,0x04(%esp)
    00000cac    movl    0x7df4-0xc8d(%ebx),%eax
    00000cb2    movl    %eax,(%esp)
    00000cb5    calll   _objc_msgSend
    00000cba    movl    0x7dbc-0xc8d(%ebx),%edx
    00000cc0    movl    %edx,0x04(%esp)
    00000cc4    movl    %eax,(%esp)
    00000cc7    calll   _objc_msgSend
    00000ccc    movl    %eax,0xe4(%ebp)
    00000ccf    movl    0x7db8-0xc8d(%ebx),%eax
    00000cd5    movl    %eax,0x04(%esp)
    00000cd9    movl    0xe4(%ebp),%eax
    00000cdc    movl    %eax,(%esp)
    00000cdf    calll   _objc_msgSend
    00000ce4    leal    (%eax,%eax),%edi
    00000ce7    movl    %edi,(%esp)
    00000cea    calll   _malloc
    00000cef    movl    %eax,%esi
    00000cf1    movl    %edi,0x08(%esp)
    00000cf5    movl    $-[ObjSample delegate],0x04(%esp)
    00000cfd    movl    %eax,(%esp)
    00000d00    calll   _memset
    00000d05    movl    $0x00000004,0x10(%esp)
    00000d0d    movl    %edi,0x0c(%esp)
    00000d11    movl    %esi,0x08(%esp)
    00000d15    movl    0x7db4-0xc8d(%ebx),%eax
    00000d1b    movl    %eax,0x04(%esp)
    00000d1f    movl    0xe4(%ebp),%eax
    00000d22    movl    %eax,(%esp)
    00000d25    calll   _objc_msgSend
    00000d2a    xorl    %edx,%edx
    00000d2c    movl    %edi,%eax
    00000d2e    shrl    $0x03,%eax
    00000d31    jmp 0x00000d34
    00000d33    incl    %edx
    00000d34    cmpl    %edx,%eax
    00000d36    ja  0x00000d33
    00000d38    movl    %esi,(%esp)
    00000d3b    calll   _free
    00000d40    movb    $0x01,_isAuthenticated-0xc8d(%ebx)
    00000d47    movzbl  _isAuthenticated-0xc8d(%ebx),%eax
    00000d4e    movl    0xf4(%ebp),%ebx
    00000d51    movl    0xf8(%ebp),%esi
    00000d54    movl    0xfc(%ebp),%edi
    00000d57    leave
    00000d58    ret
هل كانت مفيدة؟

المحلول

يقوم هذا بإعداد إطار مكدس، ويخصص 0x48 بايت للمتغيرات المحلية ويوفر إيقاف EBX و ESI و EDI، هذه هي الوظيفة القياسية بشكل جميل.

00000c79    pushl   %ebp
00000c7a    movl    %esp,%ebp
00000c7c    subl    $0x48,%esp
00000c7f    movl    %ebx,0xf4(%ebp)
00000c82    movl    %esi,0xf8(%ebp)
00000c85    movl    %edi,0xfc(%ebp)

هذه خدعة مجمعية للحصول على EBX SET لإشارة إلى التعليمات البرمجية، عندما يتم ذلك EBX يحتوي على 00000C8D.

00000c88    calll   0x00000c8d
00000c8d    popl    %ebx

هذا بت يؤمن أن الوظيفة تعمل مرة واحدة فقط، إذا قمت بالاتصال بها مرة أخرى، فستتخطا إلى النهاية (JEL 0x00000D47)

00000c8e    cmpb    $-[ObjSample delegate],_bDoOnce.26952-0xc8d(%ebx)
00000c95    jel 0x00000d47
00000c9b    movb    $-[ObjSample delegate],_bDoOnce.26952-0xc8d(%ebx)

هذا البت هو نسخ القيم المتعلقة ب EBX إلى مساحة متغيرة (مكدس) محلية، تذكر أن EBX يشير إلى الوظيفة الحالية، ولكن الإزاحة من EBX كبيرة جدا. على الأرجح هذه هي البيانات المستمرة التي يتم تثبيتها في التعليمات البرمجية ويتم إعدادها كحافز لاستدعاء وظيفة.

00000ca2    movl    0x7dc0-0xc8d(%ebx),%eax
00000ca8    movl    %eax,0x04(%esp)
00000cac    movl    0x7df4-0xc8d(%ebx),%eax
00000cb2    movl    %eax,(%esp)

استدعاء الوظيفة.

00000cb5    calll   _objc_msgSend

دفع المزيد من القيم الموجزة إلى المكدس واستدعاء آخر إلى نفس الوظيفة، هذه المرة يتم حفظ قيمة الإرجاع لاستدعاء الوظيفة إلى متغير محلي: 0xe4 (٪ EBP)

00000cba    movl    0x7dbc-0xc8d(%ebx),%edx
00000cc0    movl    %edx,0x04(%esp)
00000cc4    movl    %eax,(%esp)
00000cc7    calll   _objc_msgSend
00000ccc    movl    %eax,0xe4(%ebp)

المزيد من القيم التي تم دفعها على المكدس للحصول على مكالمة دالة، هذه المرة قيمة واحدة هي ثابتة ثابتة ل EBX، والقيمة الأخرى هي قيمة الإرجاع من المكالمة السابقة.

00000ccf    movl    0x7db8-0xc8d(%ebx),%eax
00000cd5    movl    %eax,0x04(%esp)
00000cd9    movl    0xe4(%ebp),%eax
00000cdc    movl    %eax,(%esp)
00000cdf    calll   _objc_msgSend

خذ قيمة الإرجاع من تلك المكالمة، ومضاعفة ذلك و malloc تلك الذاكرة.

00000ce4    leal    (%eax,%eax),%edi
00000ce7    movl    %edi,(%esp)
00000cea    calll   _malloc

ملء الذاكرة مع البايت الموجود في [مندوب OBJSample

00000cef    movl    %eax,%esi
00000cf1    movl    %edi,0x08(%esp)
00000cf5    movl    $-[ObjSample delegate],0x04(%esp)
00000cfd    movl    %eax,(%esp)
00000d00    calll   _memset

إرسال رسالة أخرى، هذه إحدى الحجج، 0xE4 (٪ EBP)، ثابت من EBX، MallocD PTR، حجم Malloc، 4. يفترض أن هذا يرسل الرسالة في المخزن المؤقت Malloc'd الخاص بنا، (المخزن المؤقت صحرا مؤقتا، بدلا من العودة إلى المتصل)

00000d05    movl    $0x00000004,0x10(%esp)
00000d0d    movl    %edi,0x0c(%esp)
00000d11    movl    %esi,0x08(%esp)
00000d15    movl    0x7db4-0xc8d(%ebx),%eax
00000d1b    movl    %eax,0x04(%esp)
00000d1f    movl    0xe4(%ebp),%eax
00000d22    movl    %eax,(%esp)
00000d25    calll   _objc_msgSend

مسح EDX وحفظ قيمة الإرجاع من مكالمة SendMessage إلى EDI.

00000d2a    xorl    %edx,%edx
00000d2c    movl    %edi,%eax

eax >> 3, ، ومن بعد while (edx < eax) ++edx; هذا لا معنى له الكثير من المعنى.

00000d2e    shrl    $0x03,%eax
00000d31    jmp 0x00000d34
00000d33    incl    %edx
00000d34    cmpl    %edx,%eax
00000d36    ja  0x00000d33

ذاكرة mallocd

00000d38    movl    %esi,(%esp)
00000d3b    calll   _free

تعيين _isauthenticated إلى True، قم أيضا بتعيين قيمة الإرجاع إلى True. يبدو أن هذا المتغير هو في التعليمات البرمجية، أو ربما عالمي.

00000d40    movb    $0x01,_isAuthenticated-0xc8d(%ebx)
00000d47    movzbl  _isAuthenticated-0xc8d(%ebx),%eax

استعادة السجلات والعودة.

00000d4e    movl    0xf4(%ebp),%ebx
00000d51    movl    0xf8(%ebp),%esi
00000d54    movl    0xfc(%ebp),%edi
00000d57    leave
00000d58    ret

نصائح أخرى

المهمة الصعبة ... مجمعك هو روتين فقط، لكنه يشير إلى الروتينات الفرعية الأخرى والمتغيرات العالمية أو الثابتة، لذلك فإن أفضل ما يمكن أن نفعله هو فكرة عن ما يعادلها بلغة أكثر قابلية للقراءة. ولكن ... دعونا نحاول! (C - لغة مثل)

int unknown_function(/* Parameters? */)
{
static char bDoOnce;
static char isAuthenticated;
uint32 tmp1,tmp2,tmp3;
void *p;
int i;

       if (bDoOnce == ObjSample_delegate) {
             return isAuthenticated;
       }
       bDoOnce = ObjSample_delegate;
       tmp1= objc_msgSend(some_data1, some_data2);
       tmp2 = objc_msgSend(tmp1, some_data3);
       tmp3 = objc_msgSend(tmp2, some_data4);
       p = malloc(tmp3*2);
       memset(p, ObjSample_delegate, tmp3*2);
       objc_msgSend(tmp2,some_data5,p, tmp3*2,4);
       for (i = 0; i < tmp3/4; ++i) {
       }
       free(p);
       isAuthenticated = 1;
       return isAuthenticated;
}

UHM ... لا توجد معلومات كافية لمعرفة ما الذي يحدث حقا (لا يعني أنني قد فعلت شيئا خاطئا؛)) يحتوي البرنامج على الكثير من "Some_Data"، ويبدو أن الفارغة للدورة هنا فقط لاستهلاك وحدة المعالجة المركزية. UHM ... هل هي وظيفة جمعها جنو Obsesivec؟

عذرا، حاولت، ولكن لا أستطيع أن أقول أكثر فائدة. على أي حال، آمل أن يساعدك. يعتبر

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top