Audio HAL: fixes for issues discovered after client conversion

Several issues addressed:

  -- added IDevice.supportsAudioPatches to query whether
     create/removeAudioPatch is actually supported by HAL;

  -- IStreamOutCallback proxy needs to be owned by IStreamOut
     implementation. In order for the client to reset the reference,
     added method IStreamOut.clearCallback;

  -- IDevice.open{Input|Output}Stream need to return a "suggested" audio
     config from HAL;

  -- code for converting between system/audio.h and HIDL
     data structures has been moved to
     android.hardware.audio.common@2.0-util library for reuse;

  -- added a workaround for the issue with QC effects HAL trying to write
     into the input parameters buffer, which is r/o by Binder design.

Bug: 30222631
Change-Id: I64af24d79c12d6ac3b0f87d085a821913e29237b
Test: tried using with WIP HIDL client on N5X
diff --git a/audio/effect/2.0/default/Effect.cpp b/audio/effect/2.0/default/Effect.cpp
index 82d0292..6553da4 100644
--- a/audio/effect/2.0/default/Effect.cpp
+++ b/audio/effect/2.0/default/Effect.cpp
@@ -14,7 +14,6 @@
  * limitations under the License.
  */
 
-#include <memory>
 #include <memory.h>
 
 #define LOG_TAG "EffectHAL"
@@ -56,10 +55,15 @@
 }
 
 // static
-template<typename T> void Effect::hidlVecToHal(
-        const hidl_vec<T>& vec, uint32_t* halDataSize, void** halData) {
-    *halDataSize = static_cast<T>(vec.size() * sizeof(T));
-    *halData = static_cast<void*>(const_cast<T*>(&vec[0]));
+template<typename T> std::unique_ptr<uint8_t[]> Effect::hidlVecToHal(
+        const hidl_vec<T>& vec, uint32_t* halDataSize) {
+    // Due to bugs in HAL, they may attempt to write into the provided
+    // input buffer. The original binder buffer is r/o, thus it is needed
+    // to create a r/w version.
+    *halDataSize = vec.size() * sizeof(T);
+    std::unique_ptr<uint8_t[]> halData(new uint8_t[*halDataSize]);
+    memcpy(&halData[0], &vec[0], *halDataSize);
+    return halData;
 }
 
 // static
@@ -393,12 +397,13 @@
 Return<void> Effect::setAndGetVolume(
         const hidl_vec<uint32_t>& volumes, setAndGetVolume_cb _hidl_cb)  {
     uint32_t halDataSize;
-    void *halData;
-    hidlVecToHal(volumes, &halDataSize, &halData);
+    std::unique_ptr<uint8_t[]> halData = hidlVecToHal(volumes, &halDataSize);
     uint32_t halResultSize = halDataSize;
     uint32_t halResult[volumes.size()];
     Result retval = sendCommandReturningData(
-            EFFECT_CMD_SET_VOLUME, "SET_VOLUME", halDataSize, halData, &halResultSize, halResult);
+            EFFECT_CMD_SET_VOLUME, "SET_VOLUME",
+            halDataSize, &halData[0],
+            &halResultSize, halResult);
     hidl_vec<uint32_t> result;
     if (retval == Result::OK) {
         result.setToExternal(&halResult[0], halResultSize);
@@ -528,13 +533,12 @@
         uint32_t resultMaxSize,
         command_cb _hidl_cb)  {
     uint32_t halDataSize;
-    void *halData;
-    hidlVecToHal(data, &halDataSize, &halData);
+    std::unique_ptr<uint8_t[]> halData = hidlVecToHal(data, &halDataSize);
     uint32_t halResultSize = resultMaxSize;
     std::unique_ptr<uint8_t[]> halResult(new uint8_t[halResultSize]);
     memset(&halResult[0], 0, halResultSize);
     status_t status = (*mHandle)->command(
-            mHandle, commandId, halDataSize, halData, &halResultSize, &halResult[0]);
+            mHandle, commandId, halDataSize, &halData[0], &halResultSize, &halResult[0]);
     hidl_vec<uint8_t> result;
     if (status == OK) {
         result.setToExternal(&halResult[0], halResultSize);