iOS 应用程序,类突然消失,分配崩溃

发布于 2024-09-13 15:24:22 字数 1645 浏览 4 评论 0原文

这是一个奇怪的现象。当我在处理我的应用程序时,这个问题时不时地出现,然后它总是神秘地消失。今天,它拒绝消失。

我的应用程序使用两个视图控制器来处理自动旋转。有时,Objective-C 找不到我的类。例如 [OneViewController alloc] 将崩溃。我添加了一个函数来捕获这种状态,即使我在运行自己的一行代码之前调用它,事情仍然会被破坏。我以此来证明,无论什么问题,都不是我编写的任何错误代码造成的。

有人知道为什么普遍善良不会是一个常数吗?

void verifyUniversalGoodness()
{
 id portrait_class, landscape_class;

 portrait_class = NSClassFromString(@"OneViewController");
 landscape_class = NSClassFromString(@"OtherViewController");
 NSLog(@"CHECKING GOODNESS: portrait %@, landscape %@", portrait_class, landscape_class);
 if (portrait_class == nil || landscape_class == nil)
  exit(0);
}

int main( int argc, char *argv[] )
{
    verifyUniversalGoodness();

    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
    int retVal = UIApplicationMain(argc, argv, nil, nil);
    [pool release];
    return retVal;

}

如果我让它运行来调用 alloc ,那么堆栈跟踪看起来是这样的......

#1  0x3356296c in _class_initialize ()
#2  0x33567dfe in prepareForMethodLookup ()
#3  0x33565168 in lookUpMethod ()
#4  0x33562914 in _class_lookupMethodAndLoadCache ()
#5  0x3356264a in objc_msgSend_uncached ()
#6  0x000de704 in -[MyAppDelegate finishStartup] (self=0x61c9a0, _cmd=0x303117) at /Users/michael.toy/PROJECT/MyAppDelegate.mm:180
#7  0x32b77904 in __NSFireDelayedPerform ()
#8  0x32c23d22 in CFRunLoopRunSpecific ()
#9  0x32c234e0 in CFRunLoopRunInMode ()
#10 0x30d620da in GSEventRunModal ()
#11 0x30d62186 in GSEventRun ()
#12 0x314d54c8 in -[UIApplication _run] ()
#13 0x314d39f2 in UIApplicationMain ()
#14 0x000e13a8 in main (argc=1, argv=0x2ffff5a8) at /Users/michael.toy/PROJECT/main.mm:38

This is a weird one. On and off as I have been working on my application, this problem has popped up, and then it has always mysteriously vanished. Today it is refusing to vanish.

My app uses two view controllers to handle auto rotation. Sometimes, Objective-C can't find my classes. For example [OneViewController alloc] will crash. I added a function to catch this state, and even if I call it before I run a single line of my own code, things are still broken. I take this to prove that whatever is wrong, it is not with any bad code I may have written.

Anyone have any idea why universalGoodness would not be a constant?

void verifyUniversalGoodness()
{
 id portrait_class, landscape_class;

 portrait_class = NSClassFromString(@"OneViewController");
 landscape_class = NSClassFromString(@"OtherViewController");
 NSLog(@"CHECKING GOODNESS: portrait %@, landscape %@", portrait_class, landscape_class);
 if (portrait_class == nil || landscape_class == nil)
  exit(0);
}

int main( int argc, char *argv[] )
{
    verifyUniversalGoodness();

    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
    int retVal = UIApplicationMain(argc, argv, nil, nil);
    [pool release];
    return retVal;

}

Here's what a stack trace looks like if I let it run to call of alloc ...

#1  0x3356296c in _class_initialize ()
#2  0x33567dfe in prepareForMethodLookup ()
#3  0x33565168 in lookUpMethod ()
#4  0x33562914 in _class_lookupMethodAndLoadCache ()
#5  0x3356264a in objc_msgSend_uncached ()
#6  0x000de704 in -[MyAppDelegate finishStartup] (self=0x61c9a0, _cmd=0x303117) at /Users/michael.toy/PROJECT/MyAppDelegate.mm:180
#7  0x32b77904 in __NSFireDelayedPerform ()
#8  0x32c23d22 in CFRunLoopRunSpecific ()
#9  0x32c234e0 in CFRunLoopRunInMode ()
#10 0x30d620da in GSEventRunModal ()
#11 0x30d62186 in GSEventRun ()
#12 0x314d54c8 in -[UIApplication _run] ()
#13 0x314d39f2 in UIApplicationMain ()
#14 0x000e13a8 in main (argc=1, argv=0x2ffff5a8) at /Users/michael.toy/PROJECT/main.mm:38

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

秋心╮凉 2024-09-20 15:24:30

portrait_class/landscape_class 应该是一个 Class 对象,而不是 id 对象:(

typedef struct objc_class *Class;
typedef struct objc_object {
    Class isa;
} *id;

来自 objc.h)

portrait_class/landscape_class should be a Class object, not id object:

typedef struct objc_class *Class;
typedef struct objc_object {
    Class isa;
} *id;

(That's from objc.h)

攒一口袋星星 2024-09-20 15:24:29

我不知道答案,但我对 NSClassFromString() 和 NSBundle 的 -(Class)classNamed:(NSString *)className 上的不同措辞感到震惊

“由aClassName命名的类对象,
如果没有该名称的类,则为零
当前已加载*。如果类名是
nil,返回nil。”

vs

“className 的 Class 对象。
如果 className 不是 1,则返回 nil
与相关的类
接收器或如果有错误
加载包含的可执行代码
类的实现。”

因此 NSClassFromString() 似乎并不意味着实际加载该类的命令。

I don't know the answer, but I was struck by the different wording on NSClassFromString() and NSBundle's -(Class)classNamed:(NSString *)className

"The class object named by aClassName,
or nil if no class by that name is
currently loaded*. If aClassName is
nil, returns nil."

vs

"The Class object for className.
Returns nil if className is not one
of the classes associated with the
receiver or if there is an error
loading the executable code containing
the class implementation."

So NSClassFromString() doesn't seem to imply an order to actually load the class.

醉城メ夜风 2024-09-20 15:24:28

感谢您的所有回复。这让我更仔细地审视这个问题。事实证明,我关心的类位于一个库中,而 main 类位于另一个库中,并且这两个库都链接到我的最终二进制文件中。

我需要将 -Wl,-ObjC 添加到我的链接行,这似乎已经修复了问题,并且 universalGoodness 现在已恢复。我不知道是什么触发了需要这样做的州,但我很高兴能重新开始工作。

Thank you for all your responses. It got me looking closer at the problem. It turns out that the class I care about is in one library, and the main is in another library, and both libraries are linked into my final binary.

I needed to add -Wl,-ObjC to my link line, and that seems to have fixed things and universalGoodness is now restored. I have no idea what triggered the state where this was needed, but I am happy to be back in business.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文