merge in mnc-release history after reset to mnc-dev
diff --git a/include/hardware/keymaster_defs.h b/include/hardware/keymaster_defs.h
index 77067d5..04d1228 100644
--- a/include/hardware/keymaster_defs.h
+++ b/include/hardware/keymaster_defs.h
@@ -84,9 +84,8 @@
                                                            boot. */
 
     /* User authentication */
-    KM_TAG_ALL_USERS = KM_BOOL | 500,          /* If key is usable by all users. */
-    KM_TAG_USER_ID = KM_INT | 501,             /* ID of authorized user.  Disallowed if
-                                                  KM_TAG_ALL_USERS is present. */
+    KM_TAG_ALL_USERS = KM_BOOL | 500,          /* Reserved for future use -- ignore */
+    KM_TAG_USER_ID = KM_INT | 501,             /* Reserved for future use -- ignore */
     KM_TAG_USER_SECURE_ID = KM_LONG_REP | 502, /* Secure ID of authorized user or authenticator(s).
                                                   Disallowed if KM_TAG_ALL_USERS or
                                                   KM_TAG_NO_AUTH_REQUIRED is present. */
@@ -103,9 +102,8 @@
                                                   device is powered off. */
 
     /* Application access control */
-    KM_TAG_ALL_APPLICATIONS = KM_BOOL | 600, /* If key is usable by all applications. */
-    KM_TAG_APPLICATION_ID = KM_BYTES | 601,  /* ID of authorized application. Disallowed if
-                                                KM_TAG_ALL_APPLICATIONS is present. */
+    KM_TAG_ALL_APPLICATIONS = KM_BOOL | 600, /* Reserved for future use -- ignore */
+    KM_TAG_APPLICATION_ID = KM_BYTES | 601,  /* Reserved for fugure use -- ignore */
 
     /*
      * Semantically unenforceable tags, either because they have no specific meaning or because
@@ -121,13 +119,10 @@
     /* Tags used only to provide data to or receive data from operations */
     KM_TAG_ASSOCIATED_DATA = KM_BYTES | 1000, /* Used to provide associated data for AEAD modes. */
     KM_TAG_NONCE = KM_BYTES | 1001,           /* Nonce or Initialization Vector */
-    KM_TAG_AEAD_TAG = KM_BYTES | 1002,        /* AEAD tag data.  Returned from finish() during AEAD
-                                               * encryption and provided to begin() during AEAD
-                                               * decryption.*/
-    KM_TAG_AUTH_TOKEN = KM_BYTES | 1003,      /* Authentication token that proves secure user
+    KM_TAG_AUTH_TOKEN = KM_BYTES | 1002,      /* Authentication token that proves secure user
                                                  authentication has been performed.  Structure
                                                  defined in hw_auth_token_t in hw_auth_token.h. */
-    KM_TAG_MAC_LENGTH = KM_INT | 1004,        /* MAC or AEAD authentication tag length in bits. */
+    KM_TAG_MAC_LENGTH = KM_INT | 1003,        /* MAC or AEAD authentication tag length in bits. */
 } keymaster_tag_t;
 
 /**
@@ -338,7 +333,9 @@
     KM_ERROR_MISSING_NONCE = -51,
     KM_ERROR_INVALID_NONCE = -52,
     KM_ERROR_MISSING_MAC_LENGTH = -53,
+    KM_ERROR_KEY_RATE_LIMIT_EXCEEDED = -54,
     KM_ERROR_CALLER_NONCE_PROHIBITED = -55,
+    KM_ERROR_KEY_MAX_OPS_EXCEEDED = -56,
 
     KM_ERROR_UNIMPLEMENTED = -100,
     KM_ERROR_VERSION_MISMATCH = -101,
diff --git a/modules/usbaudio/audio_hal.c b/modules/usbaudio/audio_hal.c
index 872fa93..bbea5f5 100644
--- a/modules/usbaudio/audio_hal.c
+++ b/modules/usbaudio/audio_hal.c
@@ -80,6 +80,7 @@
     struct audio_stream_out stream;
 
     pthread_mutex_t lock;               /* see note below on mutex acquisition order */
+    pthread_mutex_t pre_lock;           /* acquire before lock to avoid DOS by playback thread */
     bool standby;
 
     struct audio_device *dev;           /* hardware information - only using this for the lock */
@@ -103,7 +104,8 @@
 struct stream_in {
     struct audio_stream_in stream;
 
-    pthread_mutex_t lock; /* see note below on mutex acquisition order */
+    pthread_mutex_t lock;               /* see note below on mutex acquisition order */
+    pthread_mutex_t pre_lock;           /* acquire before lock to avoid DOS by capture thread */
     bool standby;
 
     struct audio_device *dev;           /* hardware information - only using this for the lock */
@@ -126,6 +128,13 @@
 };
 
 /*
+ * NOTE: when multiple mutexes have to be acquired, always take the
+ * stream_in or stream_out mutex first, followed by the audio_device mutex.
+ * stream pre_lock is always acquired before stream lock to prevent starvation of control thread by
+ * higher priority playback or capture thread.
+ */
+
+/*
  * Extract the card and device numbers from the supplied key/value pairs.
  *   kvpairs    A null-terminated string containing the key/value pairs or card and device.
  *              i.e. "card=1;device=42"
@@ -203,6 +212,20 @@
     return result_str;
 }
 
+void lock_input_stream(struct stream_in *in)
+{
+    pthread_mutex_lock(&in->pre_lock);
+    pthread_mutex_lock(&in->lock);
+    pthread_mutex_unlock(&in->pre_lock);
+}
+
+void lock_output_stream(struct stream_out *out)
+{
+    pthread_mutex_lock(&out->pre_lock);
+    pthread_mutex_lock(&out->lock);
+    pthread_mutex_unlock(&out->pre_lock);
+}
+
 /*
  * HAl Functions
  */
@@ -260,16 +283,14 @@
 {
     struct stream_out *out = (struct stream_out *)stream;
 
-    pthread_mutex_lock(&out->dev->lock);
-    pthread_mutex_lock(&out->lock);
-
+    lock_output_stream(out);
     if (!out->standby) {
+        pthread_mutex_lock(&out->dev->lock);
         proxy_close(&out->proxy);
+        pthread_mutex_unlock(&out->dev->lock);
         out->standby = true;
     }
-
     pthread_mutex_unlock(&out->lock);
-    pthread_mutex_unlock(&out->dev->lock);
 
     return 0;
 }
@@ -295,9 +316,9 @@
         return ret_value;
     }
 
+    lock_output_stream(out);
     /* Lock the device because that is where the profile lives */
     pthread_mutex_lock(&out->dev->lock);
-    pthread_mutex_lock(&out->lock);
 
     if (!profile_is_cached_for(out->profile, card, device)) {
         /* cannot read pcm device info if playback is active */
@@ -316,8 +337,8 @@
         }
     }
 
-    pthread_mutex_unlock(&out->lock);
     pthread_mutex_unlock(&out->dev->lock);
+    pthread_mutex_unlock(&out->lock);
 
     return ret_value;
 }
@@ -325,8 +346,8 @@
 static char * out_get_parameters(const struct audio_stream *stream, const char *keys)
 {
     struct stream_out *out = (struct stream_out *)stream;
+    lock_output_stream(out);
     pthread_mutex_lock(&out->dev->lock);
-    pthread_mutex_lock(&out->lock);
 
     char * params_str =  device_get_parameters(out->profile, keys);
 
@@ -360,17 +381,16 @@
     int ret;
     struct stream_out *out = (struct stream_out *)stream;
 
-    pthread_mutex_lock(&out->dev->lock);
-    pthread_mutex_lock(&out->lock);
+    lock_output_stream(out);
     if (out->standby) {
+        pthread_mutex_lock(&out->dev->lock);
         ret = start_output_stream(out);
+        pthread_mutex_unlock(&out->dev->lock);
         if (ret != 0) {
-            pthread_mutex_unlock(&out->dev->lock);
             goto err;
         }
         out->standby = false;
     }
-    pthread_mutex_unlock(&out->dev->lock);
 
     alsa_device_proxy* proxy = &out->proxy;
     const void * write_buff = buffer;
@@ -480,6 +500,9 @@
     out->stream.get_presentation_position = out_get_presentation_position;
     out->stream.get_next_write_timestamp = out_get_next_write_timestamp;
 
+    pthread_mutex_init(&out->lock, (const pthread_mutexattr_t *) NULL);
+    pthread_mutex_init(&out->pre_lock, (const pthread_mutexattr_t *) NULL);
+
     out->dev = adev;
     pthread_mutex_lock(&adev->lock);
     out->profile = &adev->out_profile;
@@ -639,16 +662,15 @@
 {
     struct stream_in *in = (struct stream_in *)stream;
 
-    pthread_mutex_lock(&in->dev->lock);
-    pthread_mutex_lock(&in->lock);
-
+    lock_input_stream(in);
     if (!in->standby) {
+        pthread_mutex_lock(&in->dev->lock);
         proxy_close(&in->proxy);
+        pthread_mutex_unlock(&in->dev->lock);
         in->standby = true;
     }
 
     pthread_mutex_unlock(&in->lock);
-    pthread_mutex_unlock(&in->dev->lock);
 
     return 0;
 }
@@ -676,8 +698,8 @@
         return ret_value;
     }
 
+    lock_input_stream(in);
     pthread_mutex_lock(&in->dev->lock);
-    pthread_mutex_lock(&in->lock);
 
     if (card >= 0 && device >= 0 && !profile_is_cached_for(in->profile, card, device)) {
         /* cannot read pcm device info if playback is active */
@@ -696,8 +718,8 @@
         }
     }
 
-    pthread_mutex_unlock(&in->lock);
     pthread_mutex_unlock(&in->dev->lock);
+    pthread_mutex_unlock(&in->lock);
 
     return ret_value;
 }
@@ -706,13 +728,13 @@
 {
     struct stream_in *in = (struct stream_in *)stream;
 
+    lock_input_stream(in);
     pthread_mutex_lock(&in->dev->lock);
-    pthread_mutex_lock(&in->lock);
 
     char * params_str =  device_get_parameters(in->profile, keys);
 
-    pthread_mutex_unlock(&in->lock);
     pthread_mutex_unlock(&in->dev->lock);
+    pthread_mutex_unlock(&in->lock);
 
     return params_str;
 }
@@ -750,16 +772,16 @@
 
     struct stream_in * in = (struct stream_in *)stream;
 
-    pthread_mutex_lock(&in->dev->lock);
-    pthread_mutex_lock(&in->lock);
+    lock_input_stream(in);
     if (in->standby) {
-        if (start_input_stream(in) != 0) {
-            pthread_mutex_unlock(&in->dev->lock);
+        pthread_mutex_lock(&in->dev->lock);
+        ret = start_input_stream(in);
+        pthread_mutex_unlock(&in->dev->lock);
+        if (ret != 0) {
             goto err;
         }
         in->standby = false;
     }
-    pthread_mutex_unlock(&in->dev->lock);
 
     alsa_device_profile * profile = in->profile;
 
@@ -858,6 +880,9 @@
     in->stream.read = in_read;
     in->stream.get_input_frames_lost = in_get_input_frames_lost;
 
+    pthread_mutex_init(&in->lock, (const pthread_mutexattr_t *) NULL);
+    pthread_mutex_init(&in->pre_lock, (const pthread_mutexattr_t *) NULL);
+
     in->dev = (struct audio_device *)dev;
     pthread_mutex_lock(&in->dev->lock);