I have the following code (OpenglES2.0 on iphone):
glGenBuffers(1, &tmp->m_vbo);
where tmp->m_vbo is unsigned int.
For most of the time tmp->m_vbo is valid and everything works perfect, but sometimes the returned value is 0xffffffff and first time I try to use that vbo will crash in glDrawElements.
Anyone knows what might cause this ?
Thanks.
I found the cause: there seemed to be something with the context. I used two threads, a loading thread and the main thread, each with each context (shared data). I had a "current context" value that I was checking before setting the required context (to avoid redundant SetContext calls) and somehow my "current context" value was set to the correct context, but the actual context in EAGLView was not.
The fix was to use currentContext from EAGLView for tests instead of my own value.
I had the same issue!
In Swift:
func updateContext() {
if glContext != EAGLContext.currentContext() {
EAGLContext.setCurrentContext(glContext)
}
}
Using updateContext() function right before a problem place in code solved my problem.
This return value is a -1. You should check GL error after glGenBuffers.
Related
I have problem with Thread 1: EXC_BAD_ACCESS (code=1, address=0xf00000c) and I don't know how to resolve it.
It appeared when I change some object in core date and save it and I try to pop this controller to parent.
This error is in main() with retVal.
here is some code
int retVal;
#try {
retVal = UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));
*/\ error is here**
}
#catch (NSException *exception) {
NSLog(#"%#", [exception callStackSymbols]);
#throw exception;
}
return retVal;
After re-runing app all my changes are in core data. What is more this problem is only on iOS 7. iOS 6.1 is ok.
Does someone have idea how to resolve it?
As a comment said this error is likely to be deep in your code. If the culprit is a zombie, the easiest way to find it is to run it (preferably in the latest Xcode, currently Xcode 5, as it has been improved) in profiler and choose "Zombies". When it fails, you can see the history of everything that has happened to the object.
Also, set an exception breakpoint. You may get a break when the error happens instead of in main, where the exception gets passed up.
I just had the exact same problem.
Looked here and found nothing so I started backtracking until I thought, maybe I should try Clean Build Folderđ¤
I was glad it was as easy as CLEAN BUILD FOLDER!!!
Product- Clean Build Folder(⧠â K)
đ
I resolved this problem with "Zombies" and the problem was with
[UIScrollView(UIScrollViewInternal) _notifyDidScroll]
I added
- (void)dealloc {
self.tableView.delegate = nil;
}
This problem was only in iOS 7.
Thanks for help!
I have resolve this issue only by debugging the source code and re-analyze my logic.
Below are some reference that help me lot.
EXC_BAD_ACCESS means that message was sent to a point in the memory where thereâs no instance of a class to execute it. Thus âbad accessâ.
You will get EXC_BAD_ACCESS in 3 cases:
An object is not initialized
An object is already released
Something else that is not very likely to happen
Thatâs already a good starting point. Start using the debugger, if you recently added a new object to the class youâre working on, put a breakpoint at the line before the freshly added object is used for the first time and check the values in the debugger.
Whatâs happening most though is that you will be sending a message to an overreleased object â i.e. object that is gone from the call stack. In this cases everything (and indeed everything) you will get in the console will be just :EXC_BAD_ACCESS
This is because the object is gone, there is no information what class was it, or what source file or anything else.
Please try to avoid using zombies for this.
EXC_BAD_ACCESS means there is no instance of a class to execute it.
There are 2 or more possibilities:
An object is not initialized
An object is already released
Please debug application carefully and analyze each object carefully. That might solve your issue.
I solved the same problem by finding out that the name of one of my NSString variables had the same name as one of the frameworks' class variables. Took seconds to change the name a little and problem disappeared.
With such a huge number of class variables in frameworks, it is very likely that once in a while, every programmer just by coincidence names some variable in his class exactly the same as one used somewhere in framework classes.
So it doesn't have to be Xcode bug in most cases.
In my case, I was using third-party library and I forgot to set custom-class name in Storyboard Identity Inspector
And there may be another issue which I faced today:
I had a mutable dictionary with a non-object entry try. There was a code snippet with adding a BOOL value to the dictionary. So no wonder that I got this error =).
In my case it was trying to log an Int32 with %s in print statement
in my view this is the equivalent of every other language NullPointerException,
but unlike other languages there are no hellping pointers (class name / method or line of the occurrence / god forbid a Stacktrace),
so the only thing i could do to solve it fast is to start printing main functions and views, (a very primitive solution),
create a swift: Debug.swift
add this function into Debug.swift:
public func trace(_ message: String = "", file: String = #file, function: String = #function, line: Int = #line)
{
print("**** \(file).\(function)[\(line)]: \(message)")
}
then you can use it like this:
trace("initializing")
to use it inside a var do this:
let _ = trace("initializing")
this should print something similar to this:
**** /path/to/my/file/MyFile.swift.someFunc()[18]: initializing
this is how i started adding debug lines to gain some flow record, so next time i have a EXC_BAD_ACCESS i will have a clue where the problem leis
don't forget to disable the prints during production deployment
How to write NSLog statement for
pageCache.dataSource = value;
to debug it.
In debugging found that
dataSource = (objc_object*) 0x000000
isa(objc_class*)
Thanks
This means that you dataSource is nil (i.e. there is nothing there, the pointer doesn't point to anything). This is probably the cause of whatever you are trying to debug. Make sure you are properly allocating and initializing your dataSource, or properly setting its pointer value before trying to use it.
NSLog statement to print an object to console is like this
NSLog(#"%#", pageCache.dataSource);
My program works perfectly. I assure you with my life, 0 bugs. Proudly, I tried to package the application as an .ipa file for ad-hoc distribution to my beta tester using TestFlight.
The program didn't work. Animations which are supposed to happen never happened. Network code breaks. The button to fade out the music beautifully didn't do anything at all.
It turns out that the culprit is the new and shiny blocks. When I test my program in the Simulator or on my device, I used the default "Debug" build configuration. But when I archive it for distribution (and I believe later for submission to the App Store), XCode uses another configuration which is "Release". Investigating further, the difference is due to the optimization level (you can find it on XCode's Build Settings): Debug uses None (-O0) but Release uses Fastest, Smallest (-Os). Little did I know, that it's Fastest, Smallest, and Doesn't Work (tm). Yes, blocks behave differently between those 2 configurations.
So, I set out to solve the problem. I've simplified my soon-to-change-the-world app into its bare bones, shown in the image I've attached to this post. The view controller has an instance variable x with initial value 0. If we press b, it will spawn a thread that will continuously check the value of x, changing the bottom label when x becomes 1. We can change the value of x using button a.
Here is my naive code (I'm using ARC btw):
#implementation MBIViewController
{
int _x;
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
_x = 0;
}
- (void)updateLabel
{
self.topLabel.text = [NSString stringWithFormat:#"x: %d", _x];
}
- (IBAction)buttonAPressed:(id)sender {
_x = 1;
[self updateLabel];
}
- (IBAction)buttonBPressed:(id)sender {
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
while (_x != 1) {
// keep observing for value change
}
dispatch_async(dispatch_get_main_queue(), ^{
self.bottomLabel.text = #"b changed me becase x changed!";
});
});
}
#end
_x is an instance variable, so it is reasonable to think that the block will access it using a pointer to "self", not on a local copy. And it works on the debug configuration!
But it doesn't work on Release build. So perhaps the block is using a local copy after all? OK, so let's explicitly use self:
while (self->_x != 1) {
// keep observing for value change
}
Doesn't work either in Release. OK, so let's access the damn variable directly using pointer:
int *pointerToX = &_x;
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
while (*pointerToX != 1) {
// keep observing for value change
}
// other codes
});
Still doesn't work. This is when it dawned to me that the smart optimizing compiler assumes that there is no possible way in this multithreaded world that the result of the comparison will change, so perhaps it substituted it to be always TRUE or some other voodoo.
Now, when I use this, things start working again:
while (_x != 1) {
// keep observing for value change
NSLog(#"%d", _x);
}
So, to bypass the compiler optimizing out the comparison, I resorted to making a getter:
- (int)x
{
return _x;
}
And then checking the value using that getter:
while (self.x != 1) {
// keep observing for value change
}
It now works, because self.x is actually a call to a function and the compiler is polite enough to let the function actually do its job. However, I think this is a rather convoluted way to do something so simple. Is there any other way you would have coded it, another pattern that you will use, if you are faced with the task of "observing for change of value inside a block"? Thanks a lot!
If you use a variable and do not modify it in a loop, the compiler optimization can cause the actual access to the variable to be optimized out, because your statement can be evaluated beforehand at compile time.
In order to prevent this, you can use the "volatile" keyword, which prevents the compiler from applying this type of optimization.
It does work with getters and setters, because then you need to send a message to your instance, which serves as a synchronization point.
Try declaring _x as follows:
__block int _x;
Normally variables that are also used in blocks are copied. This will indicate to the compiler that if _x is modified in the block the changes should be visible outside it. It might fix your problem.
I've seen this happen whenever i rotate a screen that has a UITableView on it. I've found out that it happens inbetween the willRotate and didRotate method calls in UIViewController My co-workers have seen it in other spots as well, usually around rotation. It hadnt started happening until very recently, and we're stumped as to how we should deal with it (google searches don't turn up the error message in its exact form). Has anyone else encountered this that knows what to do about it?
(Decided to take this out of comments and put it as an answer, since I think it's a darned good answer :)
Ha! I had an NaN calculation (div0), too. Key debugging aid: the message in question is output by NSLog(), so set a breakpoint on NSLog() and watch what the OS is doing at that time. For me, it was myUISlider.value = NaN.
To set breakpoint:
XCode 3.x
CMD-SHIFT-Y (debug window.)
Breakpoints button.
"Double-click for symbol"
Type in "NSLog" (no quotes.)
XCode 4.x
CMD-6 (breakpoints navigator.)
"+" to add breakpoint (lower left.)
Select ADD SYMBOLIC BREAKPOINT.
Symbol: NSLog
Confirm: Done.
XCode 5.x - 7.1 (at least)
(Same as 4.x, except breakpoints navigator is CMD-7, now.)
Run app, watch it break on NSLog, check the stack traces.
I've found the problem.
When you reset the frame of a tableview, it calls the delegate method tableView:heightForRowAtIndexPath: for each row in the table so it can recalculate its content size if it needs to. At that point, we do some special handling to return the height, and due to some bad assumptions in our code, we mistakenly returned NaN due to a divide by zero error (the variable we divide by was assumed to never be zero). Making sure that we do not divide by zero here fixed it.
I've spent a day trying to find the code that causes same problem and solved it within a minutes after enabling "break on exception" in Xcode. Check this tutorial to see how to enable it.
I had this problem when i was assumed that:
tableView:heightForHeaderInSection: returned an NSInteger, but it returns CGFloat...
changing:
-(NSInteger)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section
to
-(CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section
fixed my issue.
Edit:
At some point I figured out how computers work below the C level, so I thought I would share it... (I will use an register names from x86_64 as I am most familiar with them, ARM would be slightly different but analogous)
int f(){
float someFloat=5.0f;
return someFloat;
}
results in converting the value of someFloat to an integer type then copying that to a particular register: %rax then calling the return instruction.
float f(){
float someFloat=5.0f;
return someFloat;
}
results in copying the value of someFloat from its current location to a particular register: %xmm0 then calling the return instruction.
So if you have the wrong prototype the calling code will expect the value to be in the wrong place, you will end up really returning a garbage value.
This error also cost me a long time.
At the end I found my colleague wrote something like this:
UIEdgeInsets a;
a.left = (...some calculation);
button.imageEdgeInsets = a;
And I rewrote these code like this and fix the issue:
UIEdgeInsets a;
a.left = (...some calculation);
a.top = 0;
a.bottom = 0;
a.right = 0;
button.imageEdgeInsets = a;
some value of UIEdgeInsets isn't initialised properly, and it sometimes turn into a NaN value, and crash the application.
More generally, you should check whether all values of C-style structs are initialised properly.
There is an another way to reproduce the issue: using insetBy(dx:dy:) on a too small rect
You can try this yourTableview?.bounces = false. It works for me.
Hey hope someone can help as I am at my wits end with this!?
I have a UISlider. I would like it to move as progress of a task takes place (playing music).
Im setting its value as the continues events happen. (progress through the track)
-(void)updateSlider:(float)value {
NSLog(#" %f ",value);
[timeIndexSlider setValue: value animated:YES];
}
Logs state that the float value is fine..
but its just doesn't move and I get the no autorelease pool - just leaking message, that you would get from a thread without one in the console. There is no thread involved on my part.
Is there a problem updating a UISlider this often?
Is there another way of controlling the sliders movement?
Cheers
I think you're getting updates on another thread and then calling into UIKit on that thread.
Try doing a performSelectorOnMainThread with a new method that does the update (maybe taking an NSNumber object).
Are you retaining a reference to the UISlider? If not, you could be calling -setValue:animated: on a nil reference. Objective-C will allow this, without actually performing the method.
This could potentially explain why you are getting the correct float value passed into the function, but are not getting any updates...
Set a breakpoint as suggested, and make sure that the UISlider reference is not nil.
If not, try posting some code so that we can take a look.
Let us know how it goes,
Tom