[objects] Deprecate GetIsolate/Heap behind a flag

Adds a new flag v8_deprecate_get_isolate that marks
HeapObject::GetIsolate/GetHeap, Handle<T>(T*) and handle<T>(T*) as
[[deprecated]]. Deprecation warnings are not converted to errors so an
entire build can be completed to collect all the warnings.

Also adds a new script tools/collect_deprecation_stats.sh which runs the
build (assuming the flag is set) and collects the number of uses of
deprecated functions. E.g. at the time of upload, we get:

Total deprecated calls: 2265
    515 GetHeap
    842 GetIsolate
    210 handle
    698 Handle

Bug: v8:7786
Change-Id: I7043c597fa90bc77759a357ef3c2a5fefe933491
Reviewed-on: https://chromium-review.googlesource.com/1082478
Reviewed-by: Yang Guo <yangguo@chromium.org>
Commit-Queue: Dan Elphick <delphick@chromium.org>
Cr-Commit-Position: refs/heads/master@{#53475}
diff --git a/BUILD.gn b/BUILD.gn
index 0c02277..3213be5 100644
--- a/BUILD.gn
+++ b/BUILD.gn
@@ -22,6 +22,10 @@
   # Print to stdout on Android.
   v8_android_log_stdout = false
 
+  # Turns on deprecation warnings for HeapObject::GetIsolate,
+  # HeapObject::GetHeap, Handle(T* obj) and handle(T* obj).
+  v8_deprecate_get_isolate = false
+
   # Turns on all V8 debug features. Enables running V8 in a pseudo debug mode
   # within a release Chrome.
   v8_enable_debugging_features = is_debug
@@ -195,8 +199,10 @@
     "$target_gen_dir",
   ]
 
+  defines = []
+
   if (is_component_build) {
-    defines = [ "BUILDING_V8_SHARED" ]
+    defines += [ "BUILDING_V8_SHARED" ]
   }
 }
 
@@ -320,6 +326,9 @@
   if (v8_imminent_deprecation_warnings) {
     defines += [ "V8_IMMINENT_DEPRECATION_WARNINGS" ]
   }
+  if (v8_deprecate_get_isolate) {
+    defines += [ "DEPRECATE_GET_ISOLATE" ]
+  }
   if (v8_enable_i18n_support) {
     defines += [ "V8_INTL_SUPPORT" ]
   }
@@ -563,6 +572,10 @@
         v8_current_cpu == "mips64el") {
       cflags += [ "-Wshorten-64-to-32" ]
     }
+
+    if (v8_deprecate_get_isolate) {
+      cflags += [ "-Wno-error=deprecated" ]
+    }
   }
 
   if (is_win) {
diff --git a/src/handles.h b/src/handles.h
index 2513193..fc9fc80 100644
--- a/src/handles.h
+++ b/src/handles.h
@@ -97,7 +97,10 @@
                   "static type violation");
   }
 
-  V8_INLINE explicit Handle(T* object);
+#ifdef DEPRECATE_GET_ISOLATE
+  [[deprecated("Use Handle(T* object, Isolate* isolate)")]]
+#endif
+      V8_INLINE explicit Handle(T* object);
   V8_INLINE Handle(T* object, Isolate* isolate);
 
   // Allocate a new handle for the object, do not canonicalize.
@@ -166,7 +169,11 @@
 }
 
 template <typename T>
-V8_INLINE Handle<T> handle(T* object) {
+#ifdef DEPRECATE_GET_ISOLATE
+[[deprecated("Use handle(T* object, Isolate* isolate)")]]
+#endif
+    V8_INLINE Handle<T>
+    handle(T* object) {
   return Handle<T>(object);
 }
 
diff --git a/src/objects.h b/src/objects.h
index 702bc47..70b3a6d 100644
--- a/src/objects.h
+++ b/src/objects.h
@@ -1776,10 +1776,18 @@
   inline void set_map_word(MapWord map_word);
 
   // The Heap the object was allocated in. Used also to access Isolate.
-  inline Heap* GetHeap() const;
+#ifdef DEPRECATE_GET_ISOLATE
+  [[deprecated("Pass Heap explicitly")]]
+#endif
+      inline Heap*
+      GetHeap() const;
 
-  // Convenience method to get current isolate.
-  inline Isolate* GetIsolate() const;
+// Convenience method to get current isolate.
+#ifdef DEPRECATE_GET_ISOLATE
+  [[deprecated("Pass Isolate explicitly")]]
+#endif
+      inline Isolate*
+      GetIsolate() const;
 
 #define IS_TYPE_FUNCTION_DECL(Type) INLINE(bool Is##Type() const);
   HEAP_OBJECT_TYPE_LIST(IS_TYPE_FUNCTION_DECL)
diff --git a/tools/collect_deprecation_stats.sh b/tools/collect_deprecation_stats.sh
new file mode 100755
index 0000000..aa3f413
--- /dev/null
+++ b/tools/collect_deprecation_stats.sh
@@ -0,0 +1,35 @@
+#!/bin/bash
+
+# Collect the number of [[deprecated]] calls detected when compiling V8.
+# Requires "v8_deprecate_get_isolate = true" to be useful.
+
+set -e
+
+if [ -z "$1" ]; then
+  (>&2 echo "Usage: collect_deprecation_stats.sh [<outdir>|<log>]")
+  exit 1
+fi
+
+if [ -d "$1" ]; then
+  OUTDIR=$1
+  FULL_LOG=/tmp/get_isolate_deprecation.log
+  gn clean "$OUTDIR"
+  autoninja -C "$OUTDIR" > $FULL_LOG
+else
+  FULL_LOG=$1
+fi
+
+FILTERED_LOG=/tmp/filtered_isolate_deprecation.log
+UNIQUE_WARNINGS_LOG=/tmp/unique_warnings.log
+
+grep "warning:" "$FULL_LOG" | sed $'
+s|^\.\./\.\./||;
+s/: warning: \'/: /;
+
+# strip everything after deprecated function name (including template param).
+s/\(<.*>\)\\?\'.*//' > $FILTERED_LOG
+
+sort -u $FILTERED_LOG > $UNIQUE_WARNINGS_LOG
+
+echo "Total deprecated calls: $(wc -l < $UNIQUE_WARNINGS_LOG)"
+cut -f2 -d' ' $UNIQUE_WARNINGS_LOG | sort | uniq -c