2013-06-04 1 views
7

समस्या:मैं एलएलडीबी ब्रेकपॉइंट स्थिति में स्टैक सामग्री का उपयोग कैसे करूं?

मैं एक स्थिति है जहाँ हम लॉन्च के दौरान एक मीडिया प्लेबैक है, और objc_exception_throw() उस अवधि के दौरान के बारे में 5 बार मारता है, लेकिन हमेशा पकड़ा है, और यह के दक्षिण रास्ता है मिल गया है मीडिया प्लेयर ऑब्जेक्ट।

मैं या तो (ए) मैन्युअल रूप से एन बार जारी रखने के थक गया हूं, या (बी) प्लेबैक पूरा होने तक ब्रेकपॉइंट्स को अक्षम करने के लिए थक गया है।

मैं क्या कोशिश की है: मॉड्यूल के रूप में अपने लक्षित उपयोग करके मेरा अपना प्रतीकात्मक ब्रेकप्वाइंट बनाने: (यह नहीं है हमेशा बिल्कुल पांच बार समस्या)

    • ब्रेकप्वाइंट पहले पांच हिट की अनदेखी कर रही है (समस्या: कुछ भी नहीं बदला)

    मैं चाहता क्या करें:

    एक समाधान जो दिमाग में आता है, ब्रेकपॉइंट हिट करते समय स्टैक का मूल्यांकन करना है, और यदि कोई विशेष विधि या फ़ंक्शन उसमें सूचीबद्ध है तो जारी रखें। लेकिन मुझे नहीं पता कि यह कैसे करना है।

    अन्य विचार भी आपका स्वागत है।

  • उत्तर

    12

    आप इसे पायथन का उपयोग करते हैं।

    निम्नलिखित एक अनदेखी सूची और एक फ़ंक्शन को परिभाषित करता है जिसे आप ब्रेकपॉइंट के लिए कमांड के रूप में संलग्न कर सकते हैं।

    फ़ंक्शन बैकट्रैस में फ़ंक्शंस के नामों को पकड़ता है और उन नामों को अनदेखा सूची के साथ छेड़छाड़ करता है। यदि कोई नाम मेल खाता है, तो यह प्रक्रिया को जारी रखता है। यह प्रभावी ढंग से अवांछित ढेर के लिए डीबगर में गिरावट छोड़ देता है।

    (lldb) b objc_exception_throw 
    Breakpoint 1: where = libobjc.A.dylib`objc_exception_throw, address = 0x00000000000113c5 
    (lldb) script 
    Python Interactive Interpreter. To exit, type 'quit()', 'exit()' or Ctrl-D. 
    >>> ignored_functions = ['recurse_then_throw_and_catch'] 
    def continue_ignored(frame, bp_loc, dict): 
        global ignored_functions 
        names = set([frame.GetFunctionName() for frame in frame.GetThread()]) 
        all_ignored = set(ignored_functions) 
        ignored_here = all_ignored.intersection(names) 
        if len(ignored_here) > 0: 
         frame.GetThread().GetProcess().Continue() 
    
    quit() 
    
    (lldb) br comm add -F continue_ignored 1 
    (lldb) r 
    

    मैं इसे निम्न फ़ाइल के खिलाफ की कोशिश की, और इसे सफलतापूर्वक recurse_then_throw_and_catch अंदर पहली फेंक छोड़ देता है और throw_for_real अंदर फेंक दौरान डीबगर में चला जाता है।

    #import <Foundation/Foundation.h> 
    
    void 
    f(int n) 
    { 
        if (n <= 0) @throw [NSException exceptionWithName:@"plugh" reason:@"foo" userInfo:nil]; 
    
        f(n - 1); 
    } 
    
    void 
    recurse_then_throw_and_catch(void) 
    { 
        @try { 
         f(5); 
        } @catch (NSException *e) { 
         NSLog(@"Don't care: %@", e); 
        } 
    } 
    
    void 
    throw_for_real(void) 
    { 
        f(2); 
    } 
    
    int 
    main(void) 
    { 
        recurse_then_throw_and_catch(); 
        throw_for_real(); 
    } 
    

    मैं तुम्हें अपने .lldbinit को यह समारोह जोड़ने और फिर के रूप में कंसोल से जरूरत यह breakpoints से कनेक्ट कर सकता है कल्पना। (मुझे नहीं लगता कि आप Xcode के भीतर से एक स्क्रिप्ट आदेश सेट कर सकते हैं।)

    +0

    अरे, दोस्त। सबसे अच्छा जवाब मैं उम्मीद कर सकता था। – MikeyWard

    +0

    अच्छा जवाब। एकमात्र चेतावनी यह है कि अगर यह 'उपरोक्त' 'objc_exception_throw'' फ्रेम की जांच करने के बजाय, किसी भी 'ignored_functions' स्टैक पर कहीं भी दिखाई देता है' तो यह जारी रहेगा। –

    +0

    @JasonMolenda पूरी तरह से सही है।"स्टैक पर कहीं भी" जो मैंने पाया था वह था "ब्रेकपॉइंट हिट करते समय स्टैक का मूल्यांकन करें, और जारी रखें यदि कोई विशेष विधि या फ़ंक्शन उसमें सूचीबद्ध है"। 'फ्रेम' प्राप्त करने के लिए अनुकूल होना आसान होगा। गेट थ्रेड()। GetFrameAtIndex (1) .GetFunctionName() ignored_functions में: 'इसके बजाय। मुख्य अंतर्दृष्टि एक पायथन फ़ंक्शन का उपयोग ब्रेकपॉइंट कमांड के रूप में करना है। –

    1
    break command add -s python -o "return any('xyz' in f.name for f in frame.thread)" 
    

    तो एक अजगर ब्रेकपाइंट आदेश रिटर्न False, lldb चलती रहेगी। तो यह कह रहा है: यदि any स्टैक में फ्रेम के नाम पर स्ट्रिंग 'xyz' है, तो True (रोकने के लिए) वापस करें। अन्यथा यदि कोई फ्रेम उस नाम पर नहीं है, तो यह any अभिव्यक्ति False (जारी रखने के लिए) वापस आ जाएगी।

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