Home | History | Annotate | Download | only in libopensles
      1 /*
      2  * Copyright (C) 2010 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 /* sync */
     18 
     19 #include "sles_allinclusive.h"
     20 
     21 
     22 /** \brief Sync thread.
     23  *  The sync thread runs periodically to synchronize audio state between
     24  *  the application and platform-specific device driver; for best results
     25  *  it should run about every graphics frame (e.g. 20 Hz to 50 Hz).
     26  */
     27 
     28 void *sync_start(void *arg)
     29 {
     30     CEngine *this = (CEngine *) arg;
     31     for (;;) {
     32 
     33         // FIXME should be driven by cond_signal rather than polling,
     34         // or at least make the poll interval longer or configurable
     35         usleep(20000*5);
     36 
     37         object_lock_exclusive(&this->mObject);
     38         if (this->mEngine.mShutdown) {
     39             this->mEngine.mShutdownAck = SL_BOOLEAN_TRUE;
     40             // broadcast not signal, because this condition is also used for other purposes
     41             object_cond_broadcast(&this->mObject);
     42             object_unlock_exclusive(&this->mObject);
     43             break;
     44         }
     45         if (this->m3DCommit.mWaiting) {
     46             this->m3DCommit.mWaiting = 0;
     47             ++this->m3DCommit.mGeneration;
     48             // There might be more than one thread blocked in Commit, so wake them all
     49             object_cond_broadcast(&this->mObject);
     50             // here is where we would process the enqueued 3D commands
     51         }
     52         unsigned instanceMask = this->mEngine.mInstanceMask;
     53         unsigned changedMask = this->mEngine.mChangedMask;
     54         this->mEngine.mChangedMask = 0;
     55         object_unlock_exclusive(&this->mObject);
     56 
     57         // now we know which objects exist, and which of those have changes
     58 
     59         unsigned combinedMask = changedMask /* | instanceMask for debugger */;
     60         while (combinedMask) {
     61             unsigned i = ctz(combinedMask);
     62             assert(MAX_INSTANCE > i);
     63             combinedMask &= ~(1 << i);
     64             IObject *instance = (IObject *) this->mEngine.mInstances[i];
     65             // Could be NULL during construct or destroy
     66             if (NULL == instance) {
     67                 continue;
     68             }
     69 
     70             object_lock_exclusive(instance);
     71             unsigned attributesMask = instance->mAttributesMask;
     72             instance->mAttributesMask = 0;
     73 
     74             switch (IObjectToObjectID(instance)) {
     75             case SL_OBJECTID_AUDIOPLAYER:
     76                 // do something here
     77                 object_unlock_exclusive(instance);
     78 #ifdef USE_SNDFILE
     79                 if (attributesMask & (ATTR_POSITION | ATTR_TRANSPORT)) {
     80                     CAudioPlayer *audioPlayer = (CAudioPlayer *) instance;
     81                     audioPlayerTransportUpdate(audioPlayer);
     82                 }
     83 #endif
     84                 break;
     85 
     86             default:
     87                 object_unlock_exclusive(instance);
     88                 break;
     89             }
     90         }
     91     }
     92     return NULL;
     93 }
     94