Update macaroon library to 307f45bcd49f9e4088e622f23f3ce0e854345b93

Change-Id: I5e0054c0e07878d96bad781685bf23f5ae4068e2
Reviewed-on: https://weave-review.googlesource.com/2584
Reviewed-by: Alex Vakulenko <avakulenko@google.com>
diff --git a/third_party/libuweave/src/macaroon.h b/third_party/libuweave/src/macaroon.h
index c739bca..5e73b28 100644
--- a/third_party/libuweave/src/macaroon.h
+++ b/third_party/libuweave/src/macaroon.h
@@ -33,9 +33,10 @@
 } UwMacaroonDelegateeType;
 
 typedef struct {
+  UwMacaroonDelegateeType type;
   const uint8_t* id;
   size_t id_len;
-  UwMacaroonDelegateeType type;
+  UwMacaroonCaveatCloudServiceId service_id;  // Only for cloud services
   uint32_t timestamp;
 } UwMacaroonDelegateeInfo;
 
@@ -71,12 +72,11 @@
  * result object. Note that the resulting granted_scope will be the closest
  * valid scope type (to the narrower side) defined in macaroon_caveat.h.
  */
-bool uw_macaroon_validate_(
-    const UwMacaroon* macaroon,
-    const uint8_t* root_key,
-    size_t root_key_len,
-    const UwMacaroonContext* context,
-    UwMacaroonValidationResult* result);
+bool uw_macaroon_validate_(const UwMacaroon* macaroon,
+                           const uint8_t* root_key,
+                           size_t root_key_len,
+                           const UwMacaroonContext* context,
+                           UwMacaroonValidationResult* result);
 
 /** Encode a Macaroon to a byte string. */
 bool uw_macaroon_serialize_(const UwMacaroon* macaroon,
diff --git a/third_party/libuweave/src/macaroon_caveat.c b/third_party/libuweave/src/macaroon_caveat.c
index dc4ee3b..0abf7ca 100644
--- a/third_party/libuweave/src/macaroon_caveat.c
+++ b/third_party/libuweave/src/macaroon_caveat.c
@@ -26,6 +26,7 @@
     case kUwMacaroonCaveatTypeDelegateeService:
     case kUwMacaroonCaveatTypeBleSessionID:
     case kUwMacaroonCaveatTypeLanSessionID:
+    case kUwMacaroonCaveatTypeAuthenticationChallenge:
     case kUwMacaroonCaveatTypeClientAuthorizationTokenV1:
     case kUwMacaroonCaveatTypeServerAuthenticationTokenV1:
       return true;
@@ -44,11 +45,20 @@
   return false;
 }
 
+static bool is_valid_service_id_(UwMacaroonCaveatCloudServiceId service_id) {
+  switch (service_id) {
+    case kUwMacaroonCaveatCloudServiceIdNotCloudRegistered:
+    case kUwMacaroonCaveatCloudServiceIdGoogleWeave:
+      return true;
+  }
+  return false;
+}
+
 static bool create_caveat_no_value_(UwMacaroonCaveatType type,
                                     uint8_t* buffer,
                                     size_t buffer_size,
                                     UwMacaroonCaveat* new_caveat) {
-  // (buffer_size == 0 || get_buffer_size_() > buffer_size) will conver the case
+  // (buffer_size == 0 || get_buffsize_() > buffer_size) will conver the case
   // that get_buffer_size_() returns 0 (for errors), so there is no need to
   // check get_buffer_size_() == 0 again.
   if (buffer == NULL || buffer_size == 0 || new_caveat == NULL ||
@@ -134,10 +144,12 @@
     case kUwMacaroonCaveatTypeTTL24Hour:
     case kUwMacaroonCaveatTypeAppCommandsOnly:
     case kUwMacaroonCaveatTypeBleSessionID:
+    case kUwMacaroonCaveatTypeAuthenticationChallenge:
       return UW_MACAROON_ENCODING_MAX_UINT_CBOR_LEN;
 
     // Unsigned integers
     case kUwMacaroonCaveatTypeScope:
+    case kUwMacaroonCaveatTypeDelegateeService:
     case kUwMacaroonCaveatTypeExpirationAbsolute:
     case kUwMacaroonCaveatTypeDelegationTimestamp:
       return 2 * UW_MACAROON_ENCODING_MAX_UINT_CBOR_LEN;
@@ -146,11 +158,10 @@
     case kUwMacaroonCaveatTypeNonce:
     case kUwMacaroonCaveatTypeDelegateeUser:
     case kUwMacaroonCaveatTypeDelegateeApp:
-    case kUwMacaroonCaveatTypeDelegateeService:
     case kUwMacaroonCaveatTypeLanSessionID:
     case kUwMacaroonCaveatTypeClientAuthorizationTokenV1:
     case kUwMacaroonCaveatTypeServerAuthenticationTokenV1:
-      return str_len + UW_MACAROON_ENCODING_MAX_UINT_CBOR_LEN;
+      return str_len + 2 * UW_MACAROON_ENCODING_MAX_UINT_CBOR_LEN;
 
     default:
       return 0;  // For errors
@@ -238,13 +249,16 @@
 }
 
 bool uw_macaroon_caveat_create_delegatee_service_(
-    const uint8_t* id_str,
-    size_t id_str_len,
+    UwMacaroonCaveatCloudServiceId service_id,
     uint8_t* buffer,
     size_t buffer_size,
     UwMacaroonCaveat* new_caveat) {
-  return create_caveat_bstr_value_(kUwMacaroonCaveatTypeDelegateeService,
-                                   id_str, id_str_len, buffer, buffer_size,
+  if (!is_valid_service_id_(service_id)) {
+    return false;
+  }
+
+  return create_caveat_uint_value_(kUwMacaroonCaveatTypeDelegateeService,
+                                   (uint32_t)service_id, buffer, buffer_size,
                                    new_caveat);
 }
 
@@ -265,6 +279,14 @@
                                    buffer_size, new_caveat);
 }
 
+bool uw_macaroon_caveat_create_authentication_challenge_(
+    uint8_t* buffer,
+    size_t buffer_size,
+    UwMacaroonCaveat* new_caveat) {
+  return create_caveat_no_value_(kUwMacaroonCaveatTypeAuthenticationChallenge,
+                                 buffer, buffer_size, new_caveat);
+}
+
 bool uw_macaroon_caveat_create_client_authorization_token_(
     const uint8_t* str,
     size_t str_len,
@@ -336,17 +358,18 @@
 
   // If there is no additional value from the context, just compute the HMAC on
   // the current byte string.
-  uint8_t bstr_cbor_prefix[UW_MACAROON_ENCODING_MAX_UINT_CBOR_LEN] = {0};
-  size_t bstr_cbor_prefix_len = 0;
-  if (caveat_type != kUwMacaroonCaveatTypeBleSessionID) {
+  uint8_t caveat_cbor_prefix[UW_MACAROON_ENCODING_MAX_UINT_CBOR_LEN] = {0};
+  size_t caveat_cbor_prefix_len = 0;
+  if (caveat_type != kUwMacaroonCaveatTypeBleSessionID &&
+      caveat_type != kUwMacaroonCaveatTypeAuthenticationChallenge) {
     if (!uw_macaroon_encoding_encode_byte_str_len_(
-            (uint32_t)(caveat->num_bytes), bstr_cbor_prefix,
-            sizeof(bstr_cbor_prefix), &bstr_cbor_prefix_len)) {
+            (uint32_t)(caveat->num_bytes), caveat_cbor_prefix,
+            sizeof(caveat_cbor_prefix), &caveat_cbor_prefix_len)) {
       return false;
     }
 
     UwCryptoHmacMsg messages[] = {
-        {bstr_cbor_prefix, bstr_cbor_prefix_len},
+        {caveat_cbor_prefix, caveat_cbor_prefix_len},
         {caveat->bytes, caveat->num_bytes},
     };
 
@@ -356,30 +379,48 @@
   }
 
   // If there is additional value from the context.
-  if (context->ble_session_id == NULL || context->ble_session_id_len == 0) {
-    return false;
-  }
+  const uint8_t* additional_value_str = NULL;
+  size_t additional_value_str_len = 0;
+  if (caveat_type == kUwMacaroonCaveatTypeBleSessionID) {
+    if (context->ble_session_id == NULL || context->ble_session_id_len == 0) {
+      return false;
+    }
 
-  // The length here includes the length of the BLE session ID string.
-  if (!uw_macaroon_encoding_encode_byte_str_len_(
-          (uint32_t)(context->ble_session_id_len + caveat->num_bytes),
-          bstr_cbor_prefix, sizeof(bstr_cbor_prefix), &bstr_cbor_prefix_len)) {
-    return false;
+    additional_value_str = context->ble_session_id;
+    additional_value_str_len = context->ble_session_id_len;
+  } else {  // kUwMacaroonCaveatTypeAuthenticationChallenge
+    if (context->auth_challenge_str == NULL ||
+        context->auth_challenge_str_len == 0) {
+      return false;
+    }
+
+    additional_value_str = context->auth_challenge_str;
+    additional_value_str_len = context->auth_challenge_str_len;
   }
 
   uint8_t value_cbor_prefix[UW_MACAROON_ENCODING_MAX_UINT_CBOR_LEN] = {0};
   size_t value_cbor_prefix_len = 0;
   if (!uw_macaroon_encoding_encode_byte_str_len_(
-          (uint32_t)(context->ble_session_id_len), value_cbor_prefix,
+          (uint32_t)additional_value_str_len, value_cbor_prefix,
           sizeof(value_cbor_prefix), &value_cbor_prefix_len)) {
     return false;
   }
 
+  // The length here includes: 1. the header for the whole byte string; 2. the
+  // header for the addtional value part; 3. the additional value part.
+  size_t total_length =
+      caveat->num_bytes + value_cbor_prefix_len + additional_value_str_len;
+  if (!uw_macaroon_encoding_encode_byte_str_len_(
+          (uint32_t)total_length, caveat_cbor_prefix,
+          sizeof(caveat_cbor_prefix), &caveat_cbor_prefix_len)) {
+    return false;
+  }
+
   UwCryptoHmacMsg messages[] = {
-      {bstr_cbor_prefix, bstr_cbor_prefix_len},
+      {caveat_cbor_prefix, caveat_cbor_prefix_len},
       {caveat->bytes, caveat->num_bytes},
       {value_cbor_prefix, value_cbor_prefix_len},
-      {context->ble_session_id, context->ble_session_id_len},
+      {additional_value_str, additional_value_str_len},
   };
 
   return uw_crypto_hmac_(key, key_len, messages,
@@ -433,11 +474,29 @@
     }
   }
 
-  if (!uw_macaroon_caveat_get_value_bstr_(
-          caveat, &(result->delegatees[result->num_delegatees].id),
-          &(result->delegatees[result->num_delegatees].id_len))) {
-    return false;
+  if (caveat_type != kUwMacaroonCaveatTypeDelegateeService) {
+    if (!uw_macaroon_caveat_get_value_bstr_(
+            caveat, &(result->delegatees[result->num_delegatees].id),
+            &(result->delegatees[result->num_delegatees].id_len))) {
+      return false;
+    }
+    result->delegatees[result->num_delegatees].service_id =
+        kUwMacaroonCaveatCloudServiceIdNotCloudRegistered;  // Default value
+
+  } else {
+    uint32_t service_id = 0;
+    if (!uw_macaroon_caveat_get_value_uint_(caveat, &service_id)) {
+      return false;
+    }
+    if (!is_valid_service_id_((UwMacaroonCaveatCloudServiceId)service_id)) {
+      return false;
+    }
+    result->delegatees[result->num_delegatees].service_id =
+        (UwMacaroonCaveatCloudServiceId)service_id;
+    result->delegatees[result->num_delegatees].id = NULL;
+    result->delegatees[result->num_delegatees].id_len = 0;
   }
+
   result->delegatees[result->num_delegatees].type = delegatee_type;
   result->delegatees[result->num_delegatees].timestamp = issued_time;
   result->num_delegatees++;
@@ -467,6 +526,7 @@
     case kUwMacaroonCaveatTypeServerAuthenticationTokenV1:
     case kUwMacaroonCaveatTypeNonce:
     case kUwMacaroonCaveatTypeBleSessionID:
+    case kUwMacaroonCaveatTypeAuthenticationChallenge:
       return true;
 
     case kUwMacaroonCaveatTypeDelegationTimestamp:
@@ -541,6 +601,7 @@
     return false;
   }
   if (type != kUwMacaroonCaveatTypeScope &&
+      type != kUwMacaroonCaveatTypeDelegateeService &&
       type != kUwMacaroonCaveatTypeExpirationAbsolute &&
       type != kUwMacaroonCaveatTypeDelegationTimestamp) {
     // Wrong type
@@ -572,7 +633,6 @@
   if (type != kUwMacaroonCaveatTypeNonce &&
       type != kUwMacaroonCaveatTypeDelegateeUser &&
       type != kUwMacaroonCaveatTypeDelegateeApp &&
-      type != kUwMacaroonCaveatTypeDelegateeService &&
       type != kUwMacaroonCaveatTypeLanSessionID &&
       type != kUwMacaroonCaveatTypeClientAuthorizationTokenV1 &&
       type != kUwMacaroonCaveatTypeServerAuthenticationTokenV1) {
diff --git a/third_party/libuweave/src/macaroon_caveat.h b/third_party/libuweave/src/macaroon_caveat.h
index 4905667..5250ac1 100644
--- a/third_party/libuweave/src/macaroon_caveat.h
+++ b/third_party/libuweave/src/macaroon_caveat.h
@@ -24,11 +24,14 @@
 
   kUwMacaroonCaveatTypeDelegateeUser = 9,      // bstr
   kUwMacaroonCaveatTypeDelegateeApp = 10,      // bstr
-  kUwMacaroonCaveatTypeDelegateeService = 12,  // bstr
+  kUwMacaroonCaveatTypeDelegateeService = 12,  // uint
 
-  kUwMacaroonCaveatTypeAppCommandsOnly = 11,                 // no value
-  kUwMacaroonCaveatTypeBleSessionID = 16,                    // no value
-  kUwMacaroonCaveatTypeLanSessionID = 17,                    // bstr
+  kUwMacaroonCaveatTypeAppCommandsOnly = 11,  // no value
+  kUwMacaroonCaveatTypeBleSessionID = 16,     // no value
+  kUwMacaroonCaveatTypeLanSessionID = 17,     // bstr
+
+  kUwMacaroonCaveatTypeAuthenticationChallenge = 20,  // no value
+
   kUwMacaroonCaveatTypeClientAuthorizationTokenV1 = 8193,    // bstr (0x2001)
   kUwMacaroonCaveatTypeServerAuthenticationTokenV1 = 12289,  // bstr (0x3001)
 } UwMacaroonCaveatType;
@@ -40,6 +43,11 @@
   kUwMacaroonCaveatScopeTypeViewer = 20,
 } UwMacaroonCaveatScopeType;
 
+typedef enum {
+  kUwMacaroonCaveatCloudServiceIdNotCloudRegistered = 0,
+  kUwMacaroonCaveatCloudServiceIdGoogleWeave = 1,
+} UwMacaroonCaveatCloudServiceId;
+
 // For security sanity checks
 #define UW_MACAROON_CAVEAT_SCOPE_LOWEST_POSSIBLE 127
 
@@ -83,11 +91,13 @@
                                               uint8_t* buffer,
                                               size_t buffer_size,
                                               UwMacaroonCaveat* new_caveat);
-bool uw_macaroon_caveat_create_delegatee_service_(const uint8_t* id_str,
-                                                  size_t id_str_len,
-                                                  uint8_t* buffer,
-                                                  size_t buffer_size,
-                                                  UwMacaroonCaveat* new_caveat);
+
+bool uw_macaroon_caveat_create_delegatee_service_(
+    UwMacaroonCaveatCloudServiceId service_id,
+    uint8_t* buffer,
+    size_t buffer_size,
+    UwMacaroonCaveat* new_caveat);
+
 bool uw_macaroon_caveat_create_app_commands_only_(uint8_t* buffer,
                                                   size_t buffer_size,
                                                   UwMacaroonCaveat* new_caveat);
@@ -100,6 +110,11 @@
                                                size_t buffer_size,
                                                UwMacaroonCaveat* new_caveat);
 
+bool uw_macaroon_caveat_create_authentication_challenge_(
+    uint8_t* buffer,
+    size_t buffer_size,
+    UwMacaroonCaveat* new_caveat);
+
 // The string values for these two token types are optional.
 // Use str_len = 0 to indicate creating the caveats without string values.
 bool uw_macaroon_caveat_create_client_authorization_token_(
diff --git a/third_party/libuweave/src/macaroon_context.c b/third_party/libuweave/src/macaroon_context.c
index 2f1685d..e33bdd5 100644
--- a/third_party/libuweave/src/macaroon_context.c
+++ b/third_party/libuweave/src/macaroon_context.c
@@ -7,16 +7,22 @@
 bool uw_macaroon_context_create_(uint32_t current_time,
                                  const uint8_t* ble_session_id,
                                  size_t ble_session_id_len,
+                                 const uint8_t* auth_challenge_str,
+                                 size_t auth_challenge_str_len,
                                  UwMacaroonContext* new_context) {
-  if (ble_session_id == NULL && ble_session_id_len != 0) {
+  if ((ble_session_id == NULL && ble_session_id_len != 0) ||
+      (auth_challenge_str == NULL && auth_challenge_str_len != 0)) {
     return false;
   }
   if (new_context == NULL) {
     return false;
   }
 
+  *new_context = (UwMacaroonContext){};
   new_context->current_time = current_time;
   new_context->ble_session_id = ble_session_id;
   new_context->ble_session_id_len = ble_session_id_len;
+  new_context->auth_challenge_str = auth_challenge_str;
+  new_context->auth_challenge_str_len = auth_challenge_str_len;
   return true;
 }
diff --git a/third_party/libuweave/src/macaroon_context.h b/third_party/libuweave/src/macaroon_context.h
index c230eb7..762f232 100644
--- a/third_party/libuweave/src/macaroon_context.h
+++ b/third_party/libuweave/src/macaroon_context.h
@@ -15,11 +15,15 @@
   uint32_t current_time;  // In number of seconds since Jan 1st 2000 00:00:00
   const uint8_t* ble_session_id;  // Only for BLE
   size_t ble_session_id_len;
+  const uint8_t* auth_challenge_str;
+  size_t auth_challenge_str_len;
 } UwMacaroonContext;
 
 bool uw_macaroon_context_create_(uint32_t current_time,
                                  const uint8_t* ble_session_id,
                                  size_t ble_session_id_len,
+                                 const uint8_t* auth_challenge_str,
+                                 size_t auth_challenge_str_len,
                                  UwMacaroonContext* new_context);
 
 #endif  // LIBUWEAVE_SRC_MACAROON_CONTEXT_