- case mRemoveEvent:
- if (inEvent->getWorkLoop()) {
- if (eventChain == inEvent)
- eventChain = inEvent->getNext();
- else {
- IOEventSource *event, *next;
-
- event = eventChain;
- while ((next = event->getNext()) && next != inEvent)
- event = next;
-
- if (!next) {
- res = kIOReturnBadArgument;
- break;
- }
- event->setNext(inEvent->getNext());
- }
-
- inEvent->setWorkLoop(0);
- inEvent->setNext(0);
- inEvent->release();
- SETP(&fFlags, kLoopRestart);
- }
- break;
+IOReturn
+IOWorkLoop::_maintRequest(void *inC, void *inD, void *, void *)
+{
+ maintCommandEnum command = (maintCommandEnum) (uintptr_t) inC;
+ IOEventSource *inEvent = (IOEventSource *) inD;
+ IOReturn res = kIOReturnSuccess;
+
+ switch (command) {
+ case mAddEvent:
+ if (!inEvent->getWorkLoop()) {
+ SETP(&fFlags, kLoopRestart);
+
+ inEvent->retain();
+ inEvent->setWorkLoop(this);
+ inEvent->setNext(NULL);
+
+ /* Check if this is a passive or active event source being added */
+ if (eventSourcePerformsWork(inEvent)) {
+ if (!eventChain) {
+ eventChain = inEvent;
+ } else {
+ IOEventSource *event, *next;
+
+ for (event = eventChain; (next = event->getNext()); event = next) {
+ ;
+ }
+ event->setNext(inEvent);
+ }
+ } else {
+ if (!passiveEventChain) {
+ passiveEventChain = inEvent;
+ } else {
+ IOEventSource *event, *next;
+
+ for (event = passiveEventChain; (next = event->getNext()); event = next) {
+ ;
+ }
+ event->setNext(inEvent);
+ }
+ }
+ IOStatisticsAttachEventSource();
+ }
+ break;
+
+ case mRemoveEvent:
+ if (inEvent->getWorkLoop()) {
+ IOStatisticsDetachEventSource();
+
+ if (eventSourcePerformsWork(inEvent)) {
+ if (eventChain == inEvent) {
+ eventChain = inEvent->getNext();
+ } else {
+ IOEventSource *event, *next = NULL;
+
+ event = eventChain;
+ if (event) {
+ while ((next = event->getNext()) && (next != inEvent)) {
+ event = next;
+ }
+ }
+
+ if (!next) {
+ res = kIOReturnBadArgument;
+ break;
+ }
+ event->setNext(inEvent->getNext());
+ }
+ } else {
+ if (passiveEventChain == inEvent) {
+ passiveEventChain = inEvent->getNext();
+ } else {
+ IOEventSource *event, *next = NULL;
+
+ event = passiveEventChain;
+ if (event) {
+ while ((next = event->getNext()) && (next != inEvent)) {
+ event = next;
+ }
+ }
+
+ if (!next) {
+ res = kIOReturnBadArgument;
+ break;
+ }
+ event->setNext(inEvent->getNext());
+ }
+ }
+
+ inEvent->setWorkLoop(NULL);
+ inEvent->setNext(NULL);
+ inEvent->release();
+ SETP(&fFlags, kLoopRestart);
+ }
+ break;
+
+ default:
+ return kIOReturnUnsupported;
+ }