• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: Accessing user interface from ioProc
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Accessing user interface from ioProc


  • Subject: Re: Accessing user interface from ioProc
  • From: Michael Thornburgh <email@hidden>
  • Date: Thu, 20 Nov 2003 00:05:02 -0800

there are a few different problems going on here.

the first, related to the error message you got: almost all interesting Cocoa methods, especially those in the AppKit, require an NSAutoreleasePool to be active for memory management. the thread in which the IOProc executes has no NSAutoreleasePool automatically in place for you. if you wanted a pool in place in your IOProc (which you don't, see below), you'd do something like

OSStatus myIOProc (80 gazillion parameters...)
{
NSAutoreleasePool * pool = [NSAutoreleasePool new];

// do all your work, send messages to Cocoa objects, etc

[pool release];
return noErr;
}

second: memory allocation (and therefore, object creation) is not recommended in your IOProc. the time available to do the work in your IOProc is constrained, and malloc and its buddies can cause swapping, paging, and waiting on very busy locks, which can cause unpredictable and long pauses, possibly causing your IOProc to overload (glitch). since you got a warning message about no NSAutoreleasePool being in place, that means an object was getting created and was trying to be autoreleased. creating an NSAutoreleasePool would create yet another object at IOProc time. not having one in place is even worse, though -- the NSCFNumber being created isn't being released at all, which is a memory leak. eventually you'll run out of memory.

second-and-a-half: updating cocoa view objects on the screen can also take super long, and shouldn't be done in the IOProc.

third: almost none of the interesting AppKit objects are inherently thread-safe, and in particular, UI objects should only be updated in the main thread. updating those objects from threads other than the main one can (and probably will) result in drawing glitches and inconsistencies. from your IOProc, you can queue up something to happen in the main thread to actually do your UI updating, see -[NSObject performSelectorOnMainThread:withObject:waitUntilDone:] for more information (and you _don't_ want to waitUntilDone, of course!).

-mike


On Nov 19, 2003, at 8:09 PM, Michael Bonnice wrote:

In my application, I listen to the input device and calculate an FFT
all within my ioProc. This works, and I can print the results using
fprintf(stderr, ...) from my ioProc. Now I'm ready to put the results
into my user interface.

This is an Objective-C program, and I'm new to Objective-C and Cocoa.
Naturally, before I've even got the grip of the object hierarchy and
the flow of control, I need to send a message to an object while in an
ioProc, and I don't know what scope the ioProc is in (or if this is
even a meaningful concept?)

There is a text field in my interface window that should display the
result. I stored a reference to that field, calculate the result, then
send the field the message to display the result. It does display it,
but I get an error message in the console each time I send the message:

2003-11-19 21:05:44.854 Tuner[466] *** _NSAutoreleaseNoPool(): Object
0x36b3d0 of class NSCFNumber autoreleased with no pool in place - just
leaking

Any ideas how to fix this?

Mike

Code fragments:

@interface TunerController : NSObject
{
...
IBOutlet id freqField; // the user interface item, a text field
...
}
...
@end

@implementation TunerController

- (void)awakeFromNib
{
[tuner setup]; // this will initialize our CoreAudio data
...
[tuner setLeftFreqField: freqField]; // tell the tuner where to
show the left frequency
}
..

@end

@interface Tuner : NSObject
{

...

IBOutlet id leftFreqField; // field showing the
frequency of the left channel
}

...
- (void)setLeftFreqField:(id)field;

@end

// define a C struct from the Obj-C object so audio callback can access
data
typedef struct {
@defs(Tuner);
} tunerdef;

// this is the audio processing callback

OSStatus inappIOProc (AudioDeviceID inDevice, const AudioTimeStamp*
inNow, const AudioBufferList* inInputData,
const AudioTimeStamp* inInputTime,
AudioBufferList* outOutputData, const AudioTimeStamp* inOutputTime,
void* defptr)
{
tunerdef* def = defptr; // get access to Tuner's data
float leftFreq;

// do the FFT math here, the answer is in leftFreq
..
[def->leftFreqField setDoubleValue: leftFreq]; // display
the result !!!!!!!!!!!!!! problem here !!!!!!!!!!
}

@implementation Tuner

- (void)setLeftFreqField:(id)field
{
leftFreqField = field; // store the field id in a place where the
ioProc can get it
}

@end
_______________________________________________
coreaudio-api mailing list | email@hidden
Help/Unsubscribe/Archives: http://www.lists.apple.com/mailman/listinfo/coreaudio-api
Do not post admin requests to the list. They will be ignored.
_______________________________________________
coreaudio-api mailing list | email@hidden
Help/Unsubscribe/Archives: http://www.lists.apple.com/mailman/listinfo/coreaudio-api
Do not post admin requests to the list. They will be ignored.

  • Follow-Ups:
    • Re: Accessing user interface from ioProc
      • From: James McCartney <email@hidden>
References: 
 >Accessing user interface from ioProc (From: Michael Bonnice <email@hidden>)

  • Prev by Date: Re: Accessing user interface from ioProc
  • Next by Date: AU from scratch [was: Re: can't compile SampleEffect & MultitapAU]
  • Previous by thread: Re: Accessing user interface from ioProc
  • Next by thread: Re: Accessing user interface from ioProc
  • Index(es):
    • Date
    • Thread