Bug 1186791 (part 1) - Replace nsBaseHashtable::EnumerateRead() calls in storage/ with iterators. r=mak.
authorNicholas Nethercote <nnethercote@mozilla.com>
Thu, 29 Oct 2015 16:04:41 -0700
changeset 270383 582ecb12478ae567b439bb5aa01a1ac3b9551e61
parent 270382 dd5adab01830fec1b51918a9626702fea0d454f7
child 270384 15aad0a5b3cb1695bacaf3e4ecb40339cb7a2a1c
push id29612
push userkwierso@gmail.com
push dateFri, 30 Oct 2015 23:36:00 +0000
treeherdermozilla-central@1596ab6985cb [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmak
bugs1186791
milestone45.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1186791 (part 1) - Replace nsBaseHashtable::EnumerateRead() calls in storage/ with iterators. r=mak.
storage/mozStorageBindingParams.cpp
storage/mozStorageBindingParams.h
--- a/storage/mozStorageBindingParams.cpp
+++ b/storage/mozStorageBindingParams.cpp
@@ -150,59 +150,16 @@ BindingParams::unlock(Statement *aOwning
 }
 
 const mozIStorageBindingParamsArray *
 BindingParams::getOwner() const
 {
   return mOwningArray;
 }
 
-PLDHashOperator
-AsyncBindingParams::iterateOverNamedParameters(const nsACString &aName,
-                                               nsIVariant *aValue,
-                                               void *voidClosureThunk)
-{
-  NamedParameterIterationClosureThunk *closureThunk =
-    static_cast<NamedParameterIterationClosureThunk *>(voidClosureThunk);
-
-  // We do not accept any forms of names other than ":name", but we need to add
-  // the colon for SQLite.
-  nsAutoCString name(":");
-  name.Append(aName);
-  int oneIdx = ::sqlite3_bind_parameter_index(closureThunk->statement,
-                                              name.get());
-
-  if (oneIdx == 0) {
-    nsAutoCString errMsg(aName);
-    errMsg.AppendLiteral(" is not a valid named parameter.");
-    closureThunk->err = new Error(SQLITE_RANGE, errMsg.get());
-    return PL_DHASH_STOP;
-  }
-
-  // XPCVariant's AddRef and Release are not thread-safe and so we must not do
-  // anything that would invoke them here on the async thread.  As such we can't
-  // cram aValue into self->mParameters using ReplaceObjectAt so that we can
-  // freeload off of the BindingParams::Bind implementation.
-  int rc = variantToSQLiteT(BindingColumnData(closureThunk->statement,
-                                              oneIdx - 1),
-                            aValue);
-  if (rc != SQLITE_OK) {
-    // We had an error while trying to bind.  Now we need to create an error
-    // object with the right message.  Note that we special case
-    // SQLITE_MISMATCH, but otherwise get the message from SQLite.
-    const char *msg = "Could not covert nsIVariant to SQLite type.";
-    if (rc != SQLITE_MISMATCH)
-      msg = ::sqlite3_errmsg(::sqlite3_db_handle(closureThunk->statement));
-
-    closureThunk->err = new Error(rc, msg);
-    return PL_DHASH_STOP;
-  }
-  return PL_DHASH_NEXT;
-}
-
 ////////////////////////////////////////////////////////////////////////////////
 //// nsISupports
 
 NS_IMPL_ISUPPORTS(
   BindingParams
 , mozIStorageBindingParams
 , IStorageBindingParamsInternal
 )
@@ -236,23 +193,54 @@ BindingParams::bind(sqlite3_stmt *aState
 already_AddRefed<mozIStorageError>
 AsyncBindingParams::bind(sqlite3_stmt * aStatement)
 {
   // We should bind by index using the super-class if there is nothing in our
   // hashtable.
   if (!mNamedParameters.Count())
     return BindingParams::bind(aStatement);
 
-  // Enumerate over everyone in the map, propagating them into mParameters if
-  // we can and creating an error immediately when we cannot.
-  NamedParameterIterationClosureThunk closureThunk = {this, aStatement, nullptr};
-  (void)mNamedParameters.EnumerateRead(iterateOverNamedParameters,
-                                       (void *)&closureThunk);
+  nsCOMPtr<mozIStorageError> err;
+
+  for (auto iter = mNamedParameters.Iter(); !iter.Done(); iter.Next()) {
+    const nsACString &key = iter.Key();
+
+    // We do not accept any forms of names other than ":name", but we need to
+    // add the colon for SQLite.
+    nsAutoCString name(":");
+    name.Append(key);
+    int oneIdx = ::sqlite3_bind_parameter_index(aStatement, name.get());
+
+    if (oneIdx == 0) {
+      nsAutoCString errMsg(key);
+      errMsg.AppendLiteral(" is not a valid named parameter.");
+      err = new Error(SQLITE_RANGE, errMsg.get());
+      break;
+    }
 
-  return closureThunk.err.forget();
+    // XPCVariant's AddRef and Release are not thread-safe and so we must not
+    // do anything that would invoke them here on the async thread.  As such we
+    // can't cram aValue into mParameters using ReplaceObjectAt so that
+    // we can freeload off of the BindingParams::Bind implementation.
+    int rc = variantToSQLiteT(BindingColumnData(aStatement, oneIdx - 1),
+                              iter.UserData());
+    if (rc != SQLITE_OK) {
+      // We had an error while trying to bind.  Now we need to create an error
+      // object with the right message.  Note that we special case
+      // SQLITE_MISMATCH, but otherwise get the message from SQLite.
+      const char *msg = "Could not covert nsIVariant to SQLite type.";
+      if (rc != SQLITE_MISMATCH) {
+        msg = ::sqlite3_errmsg(::sqlite3_db_handle(aStatement));
+      }
+      err = new Error(rc, msg);
+      break;
+    }
+  }
+
+  return err.forget();
 }
 
 
 ///////////////////////////////////////////////////////////////////////////////
 //// mozIStorageBindingParams
 
 NS_IMETHODIMP
 BindingParams::BindByName(const nsACString &aName,
--- a/storage/mozStorageBindingParams.h
+++ b/storage/mozStorageBindingParams.h
@@ -100,25 +100,14 @@ public:
 
   virtual already_AddRefed<mozIStorageError> bind(sqlite3_stmt * aStatement);
 
   explicit AsyncBindingParams(mozIStorageBindingParamsArray *aOwningArray);
   virtual ~AsyncBindingParams() {}
 
 private:
   nsInterfaceHashtable<nsCStringHashKey, nsIVariant> mNamedParameters;
-
-  struct NamedParameterIterationClosureThunk
-  {
-    AsyncBindingParams *self;
-    sqlite3_stmt *statement;
-    nsCOMPtr<mozIStorageError> err;
-  };
-
-  static PLDHashOperator iterateOverNamedParameters(const nsACString &aName,
-                                                    nsIVariant *aValue,
-                                                    void *voidClosureThunk);
 };
 
 } // namespace storage
 } // namespace mozilla
 
 #endif // mozStorageBindingParams_h