I'm developing an iOS application right now, and I have a quite high CPU usage. So I decided to profile it a bit.
With Xcode 5 things became easy, and I can see that "Thread #25" is using quite a lot of CPU. Sadly this thread is not named, and my app has external dependencies, so I don't have a means to add names for each thread.
tl;dr: How can I know who spawned this "Thread #25" ?
Related
I’m having a memory issue. I get an error message “Thread 1: EXC_BAD_ACCESS(code=1,address=…) The error is elusive, and apparently timing-dependent. On my iPad mini, it usually averages about 3 minutes between crashes, on my iPhone SE it averages 10 minutes, and on the simulator it has run for 20 hours without crashing.
I’m not successful in using the Zombie detector. (See below for my experiences with it.) So I’m trying to go over my code with a fine tooth comb to see what might be causing the crash. What are the issues that might cause an allocation error?
My app is multi-threaded. It takes sound from the microphone, processes it, and continuously updates the display with the processed results. It’s written in Swift 3, so I’m not doing any explicit mallocs or frees.
I’m looking for places in the code that might cause an error. The two things I’m looking closest at are weak references and unsafe pointers. Are there any other common programming errors that could trip me up?
(The Zombie detector is useless. The Apple Instruments User Guide says, “For iOS apps, use the Zombies template with the iOS Simulator, rather than a physical device.” I’ve ignored the warning and tried it with my iPad mini, and I can’t get it to crash. Everything runs at about 1/10 speed, and when I pause the recording, my OSX machine gets sluggish as well, displaying the spinning “Wait” cursor for minutes at a time. The total memory allocation goes up and down, but stays within limits, so there is no major memory leak. I’ve also run the Zombies instrument on the simulator as well. It’s equally sluggish, and it still doesn’t crash.)
The issue in this case turns out to be thread safety. If I set a UInt8 variable on one thread and read it on another thread, it can lead to a memory error. The setters and the getters are not thread safe.
(I’ve been programming computers most of my professional life, mostly in C, C++, and Java. I’m familiar with the multi-threading issues in these languages. I’m new to Swift 3. It simply hadn’t occurred to me up to now that setting and getting numeric variables was not an atomic operation — that an ill-timed access could cause a program to crash. I’m going to have to drastically rethink my approach to concurrency with Swift.)
I have an app that I am building for iOS 7 only and running on an iPhone 5S. The app sometimes in normal use just freezes up and won't recognize any touch interactions happen and it requires the app to be force quit. I have noticed it doing many different tasks and in different views. I have had this problem while debugging and the RAM usage is at about 65 Mb which I think is pretty good, cpu usage is in the single digits and the debugger doesn't register a crash. Where can I go from here in terms of debugging and trying to fix this pretty serious problem?
To put my comment as an answer, usually when your application freezes, it means either the CPU is doing some heavy lifting or your have a deadlock somewhere. As you mentioned that it was the CPU usage was low, my first guess was a deadlock.
Thanks to Leo Natan for suggesting that it was deadlocks, because it was. There was a specific instance where I was saving and fetching from the background thread and there was an easy solution that made it possible for me to stop fetching on the background thread.
For me, it was an endless while loop. Found it out by pausing the process and checking out the stack trace.
I'm scared to ask this question because it doesn't include specifics and doesn't have any code samples, but that's because I've encountered it on three entirely different apps that I've worked on in the past few weeks, and I'm thinking specific code might just cloud the issue.
Scoured the web and found no reference to the phenomenon I'm encountering, so I'm just going to throw this out there and hope someone else has seen the same thing:
The 'problem' is that all the iOS OpenGL apps I've built, to a man, run MUCH FASTER when I'm profiling them in Instruments than when they're running standalone. As in, a frame rate roughly twice as fast (jumping from, eg, 30fps to 60fps). This is both measured with a code-timing loop and from watching the apps run. Instruments appears to be doing something magical.
This is on a device, not the iOS simulator.
If I profile my OpenGL apps and upload to a device — specifically, iPad 3 running iOS 5.1 — via Instruments, the frame rate is just flat-out much, much faster than running standalone. There appears to be no frame skipping or shennanigans like that. It simply does the same computation at around twice the speed.
Although I'm not including any code samples, just assume I'm doing the normal stuff. OpenGL ES 2.0, with VBOs and VAOs. Multithreading some computationally intensive code areas with dispatch queues/blocks. Nothing exotic or crazy.
I'd just like to know if anyone has experienced anything vaguely similar. If not, I'll just head back to my burrow and continue stabbing myself in the leg with a fork.
Could be that when you profile, a release build is used (by default) instead of a debug build when you just hit run.
I'm a beginner in xcode and iphone iOS development while debugging the xcode it shows Thread1,Thread2,Thread3,Thread4 what these threads meant? and how it is useful in debugging can some explain?
For the purposes of debugging your own app, you really only need to worry about Thread1, or at least until such point that you start writing concurrent code (see Concurrency Programming Guide).
A thread is basically a particular path of execution of code. Thread1 is the "main thread", the one where your app does its basic operations, all of the user interface code, etc. When you start getting into more sophisticated programming, you might employ concurrency, where you send time consuming operations to a background thread/queue so that it doesn't adversely affect the user experience which is happening on the main thread.
The threads 2, 3, 4, etc. in your question, though, are system generated threads and not ones you generally need to concern yourself with. Only worry about the main thread and, if and when you get into writing concurrent code, those threads to which you are explicitly adding operations.
I'm using NSOperationQueue to manage a phase of an iOS application which is quite long so I would like to manage it asynchronously. Inside that phase I allocate big arrays in C by using directly calloc functions.
With big I mean a 1024x256 bidimensional array of floats and similar things.
If everything resides on the main thread than the app locks up while computing but everything goes fine, if, instead, I move the heavy part to a NSInvocationOperation then I got many strange results, with debugger sometimes I get a strange message in console stating
No memory available to program now: unsafe to call malloc
so I was wondering if threads managed by an operation queue have some different restrictions compared to main thread, and in case what is better to do to get around this issue.
There's no restrictions that I know of.. however, you may be hitting the edge of available RAM. Since iOS doesn't do virtual memory, when memory gets low, it'll send a warning to other apps to free up RAM. That may be the source of your issue.
Use instruments to profile how much RAM you're using. If it's more than about 20MB or so, you're probably in danger of being terminated due to excessive memory usage anyway.