)]}'
{
  "log": [
    {
      "commit": "6dd62fb91d82dedcfa3ab38c02eb0940b4ba932a",
      "tree": "5c463a944686864894c2be528a52df9d275dd221",
      "parents": [
        "f3b785ae6ea135115b54ac58cedc12b444483902"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Thu Dec 05 16:35:58 2013 -0800"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Tue Feb 18 12:52:35 2014 -0800"
      },
      "message": "Multi-client recording\n\nSupports multiple clients both at native sample rate and with resampling.\n\nChange-Id: Icea55b4fd30751761b7debaa3ce016c79e712d8d\n"
    },
    {
      "commit": "462fd2fa9eef642b0574aa7409de0bde3fec8d43",
      "tree": "65446a138d197f062bf199480b96cca4df560fcf",
      "parents": [
        "f7d89bd79d170be3b299717ac11aff62909314c5"
      ],
      "author": {
        "name": "Marco Nelissen",
        "email": "marcone@google.com",
        "time": "Mon Jan 14 14:12:05 2013 -0800"
      },
      "committer": {
        "name": "Marco Nelissen",
        "email": "marcone@google.com",
        "time": "Fri Oct 25 11:13:17 2013 -0700"
      },
      "message": "Assign blame for playback wakelocks.\n\nSet a work source for the playback wakelock, so that playback is\ncounted against the requesting app instead of the media server.\n\nChange-Id: I7329f88a288a95a582a78005a1c3d16a5a611e31\n"
    },
    {
      "commit": "030033342a6ea17003e6af38a56c7edc6d2ead01",
      "tree": "342168125e3c97f01af88dfe133f99c7f71d7e3d",
      "parents": [
        "9156ef3e11b68cc4b6d3cea77f1f63673855a6d1"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Tue Aug 06 15:40:54 2013 -0700"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Mon Aug 12 16:35:25 2013 -0700"
      },
      "message": "Clean up error handling in createTrack and openRecord\n\nOutside callers now use initCheck() to determine whether a TrackBase\nhas been created successfully, instead of relying on internal knowledge.\n\nPreviously, callers needed to know that a TrackBase was only valid if it\u0027s\ngetCbk() !\u003d 0.  For a Track (playback), they needed to know to also check\nthe track\u0027s name (track index).  Now, outsiders can just call initCheck().\n\nOther changes:\n - Return a 0 reference if track creation fails\n - Remove a dead line of code in AudioFlinger::openRecord\n\nChange-Id: If374924a3f6fd27906f625aa83dd0a1e3f506e00\n"
    },
    {
      "commit": "aac30336994235e42a92861eb83289131a6b94dd",
      "tree": "09febd07aef324753e2dad1d7ff27132d91d0167",
      "parents": [
        "deeef54487a34034dc0cfaab20b20d557224c07c"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Tue Aug 06 14:41:45 2013 -0700"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Tue Aug 06 14:41:45 2013 -0700"
      },
      "message": "Remove obsolete TrackBase::getBuffer()\n\nChange-Id: Ic39c7baa9538080bfec114bf18ff9b9986c93fed\n"
    },
    {
      "commit": "f6ed423af92a56ef54bba23eba883b1f21448b54",
      "tree": "bad2f734e3191cbfa3c72bdeadcd88f5015e6ba8",
      "parents": [
        "2eeca1f8e18106d118f7268cb9d8597539685c5c"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Tue Jul 16 11:16:27 2013 -0700"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Mon Jul 29 12:43:12 2013 -0700"
      },
      "message": "Treat mChannelCount as uint32_t consistently\n\nmChannelCount was 8-, 16-, or 32-bits\n\nChange-Id: I2cc2fedf3e33144e5c8bbd9894763282d9217f63\n"
    },
    {
      "commit": "35cc4f3127322ad3e3dd1e15e8ae29ff4b4a3af6",
      "tree": "ad534d537cd19cdb33fb5068059f3bd726e1f805",
      "parents": [
        "bd4c4fbb3b073e48963185d11a15da1fa18d2e54"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Thu Jul 25 14:21:35 2013 -0700"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Mon Jul 29 09:40:24 2013 -0700"
      },
      "message": "Remove obsolete mBufferEnd\n\nChange-Id: I507c6109d66000bb30933ca23b912a1316f55e5e\n"
    },
    {
      "commit": "bd4c4fbb3b073e48963185d11a15da1fa18d2e54",
      "tree": "00ebf9a7c78cd47ca27ca22b072142e3b21e7c04",
      "parents": [
        "afbbc6c5f6bc470d504dcf24ceb3ac21d57fb78d"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Thu Jul 25 14:21:14 2013 -0700"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Mon Jul 29 09:40:19 2013 -0700"
      },
      "message": "Remove obsolete TrackBase::step(), mStepCount, mStepServerFailed\n\nChange-Id: I6347096f066b8b19451c6472db7b0671f0cf7702\n"
    },
    {
      "commit": "65d30dd9ee498f7b3bfc033735458a6ff399c207",
      "tree": "e5fa59313d1c9ed9e61622217b92383fccac93eb",
      "parents": [
        "422801c5e9b795105f28e639c4bed5ee3f4e56f3",
        "0fea74cdbc09c1259e08215e2ea90e7988d62df8"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Fri Jul 26 23:24:50 2013 +0000"
      },
      "committer": {
        "name": "Android (Google) Code Review",
        "email": "android-gerrit@google.com",
        "time": "Fri Jul 26 23:24:50 2013 +0000"
      },
      "message": "Merge \"Remove obsolete TrackBase::reset()\""
    },
    {
      "commit": "0fea74cdbc09c1259e08215e2ea90e7988d62df8",
      "tree": "45421baddb2bab78c036dba12063e7d70b5b2082",
      "parents": [
        "fc5ea08326b510c6f82f71845d95a8758a6ab698"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Thu Jul 25 14:34:57 2013 -0700"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Thu Jul 25 14:39:31 2013 -0700"
      },
      "message": "Remove obsolete TrackBase::reset()\n\nChange-Id: I38100b7e28a12d7af8cb40ae3f4d9cb4a0ebe701\n"
    },
    {
      "commit": "bfb1b832079bbb9426f72f3863199a54aefd02da",
      "tree": "5007d22456776dc77d124be84bcfe8bc4152bbb2",
      "parents": [
        "fc5ea08326b510c6f82f71845d95a8758a6ab698"
      ],
      "author": {
        "name": "Eric Laurent",
        "email": "elaurent@google.com",
        "time": "Mon Jan 07 09:53:42 2013 -0800"
      },
      "committer": {
        "name": "Eric Laurent",
        "email": "elaurent@google.com",
        "time": "Thu Jul 25 14:08:09 2013 -0700"
      },
      "message": "AudioFlinger: offload playback, non-blocking write\n\n- Added specialized playback thread class for offload playback,\nderived from directoutput thread.\nThis thread type handles specific state transitions for offloaded\ntracks and offloading commands (pause/resume/drain/flush..) to audio HAL.\nAs opposed to other threads, does not go to standby if the track is paused.\n\n- Added support for asynchronous write and drain operations at audio HAL.\nUse a thread to handle async callback events from HAL: this avoids locking\nplayback thread mutex when executing the callback and cause deadlocks when\ncalling audio HAL functions with the playback thread mutex locked.\n\n- Better accouting for track activity: call start/stop and release Output\nmethods in audio policy manager when tracks are actually added and removed\nfrom the active tracks list.\nAdded a command thread in audio policy service to handle stop/release commands\nasynchronously and avoid deadlocks with playback thread.\n\n- Track terminated status is not a state anymore. This condition is othogonal\nto state to permitted state transitions while terminated.\n\nChange-Id: Id157f4b3277620568d8eace7535d9186602564de\n"
    },
    {
      "commit": "9f80dd223d83d9bb9077fb6baee056cee4eaf7e5",
      "tree": "79f19f80ebb7978e9bab16e1d9b835849c735592",
      "parents": [
        "9fef8d453b15a91a2b748faac2bfaff713bcf1e1"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Tue Dec 18 15:57:32 2012 -0800"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Wed Jun 12 14:33:10 2013 -0700"
      },
      "message": "New control block for AudioTrack and AudioRecord\n\nMain differences between old and new control block:\n - removes the mutex, which was a potential source of priority inversion\n - circular indices into shared buffer, which is now always a power-of-2 size\n\nChange-Id: I4e9b7fa99858b488ac98a441fa70e31dbba1b865\n"
    },
    {
      "commit": "c9b2e20f7c9a71e07ef398152709c76079decbcd",
      "tree": "7e3cbee883fbe1462e24a31b8b4af5a5911e8276",
      "parents": [
        "bf04b5860182d8f4130dcb5d6d88ee68a58c99cd"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Tue Feb 26 11:32:32 2013 -0800"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Mon Mar 04 12:58:21 2013 -0800"
      },
      "message": "Miscellaneous cleanup\n\nAbbreviation framesReady to fRdy for new systrace.\nPut inline const on one line.\nUse local copy of mState in state.\nImprove logging.\nLine length 100.\n\nChange-Id: I8201c3ce0e53fd464fd33d02544e52c342d40b68\n"
    },
    {
      "commit": "da6ef1320d0161b1640dc84d7a9c5a25860c3619",
      "tree": "86b24f64ed0bd55de10deb193290009687886192",
      "parents": [
        "99c2f923f6b04efffe949d1daf9cb7148e3cc201"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Thu Jan 10 12:31:01 2013 -0800"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Fri Feb 22 16:50:36 2013 -0800"
      },
      "message": "Update tee sink\n\nImplement rotation to reduce long-term storage use.\nImplement optional per-track tee.\nDynamically enable at runtime based on property, instead of at compile-time.\nDynamic frame count not yet implemented.\n\nBug: 8223560\nChange-Id: I3706443c6ec0cb0c6656dc288715a02ad5fea63a\n"
    },
    {
      "commit": "e3aa659e9cee7df5c12a80d285cc29ab3b2cbb39",
      "tree": "90fdb6e9da1a03f4f24691aae27ae94ff913f1c7",
      "parents": [
        "84b6440fa1d1274267deabe0bd8dc626b5548e4c"
      ],
      "author": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Tue Dec 04 12:22:46 2012 -0800"
      },
      "committer": {
        "name": "Glenn Kasten",
        "email": "gkasten@google.com",
        "time": "Wed Dec 12 12:21:59 2012 -0800"
      },
      "message": "Start isolating control block accesses in a proxy\n\nThe proxy object will eventually be the only code that understands the\ndetails of the control block.  This should make it easier to change the\ncontrol block in the future.\n\nInitial set of control block fields that are isolated:\n - sample rate\n - send level\n - volume\n\nPrepare for streaming/static separation by adding a union to the control\nblock for the new fields.\n\nFix bug in handling of max sample rate on a track.  It was only checking\nat re-configuration, not at each mix.\n\nSimplify OutputTrack::obtainBuffer.\n\nChange-Id: I2249f9d04f73a911a922ad1d7f6197292c74cd92\n"
    },
    {
      "commit": "81784c37c61b09289654b979567a42bf73cd2b12",
      "tree": "a0a3fa9225bea006c2e037a337b43bf4ba7c0743",
      "parents": [
        "4d9cef6c007afd195a8f36d35d46b359bf909331"
      ],
      "author": {
        "name": "Eric Laurent",
        "email": "elaurent@google.com",
        "time": "Mon Nov 19 14:55:58 2012 -0800"
      },
      "committer": {
        "name": "Eric Laurent",
        "email": "elaurent@google.com",
        "time": "Mon Nov 19 19:35:38 2012 -0800"
      },
      "message": "AudioFlinger files reorganization\n\nAudioflinger.cpp and Audioflinger.h files must be split to\nimprove readability and maintainability.\n\nThis CL splits the files as follows:\n\nAudioFlinger.cpp split into:\n- AudioFlinger.cpp: implementation of IAudioflinger interface and global methods\n- AFThreads.cpp: implementation of ThreadBase, PlaybackThread, MixerThread,\nDuplicatingThread, DirectOutputThread and RecordThread.\n- AFTracks.cpp: implementation of TrackBase, Track, TimedTrack, OutputTrack,\nRecordTrack, TrackHandle and RecordHandle.\n- AFEffects.cpp: implementation of EffectModule, EffectChain and EffectHandle.\n\nAudioFlinger.h is modified by inline inclusion of header files containing\nthe declaration of complex inner classes:\n- AFThreads.h: ThreadBase, PlaybackThread, MixerThread, DuplicatingThread,\nDirectOutputThread and RecordThread\n- AFEffects.h: EffectModule, EffectChain and EffectHandle\n\nAFThreads.h includes the follownig headers inline:\n- AFTrackBase.h: TrackBase\n- AFPlaybackTracks: Track, TimedTrack, OutputTrack\n- AFRecordTracks: RecordTrack\n\nChange-Id: I512ebc3a51813ab7a4afccc9a538b18125165c4c\n"
    }
  ]
}
