Backport some new protocol tests from CPython (#202)

diff --git a/src/test_typing_extensions.py b/src/test_typing_extensions.py
index ac0a269..24f51e6 100644
--- a/src/test_typing_extensions.py
+++ b/src/test_typing_extensions.py
@@ -1696,6 +1696,12 @@
     y: int
 
 
+skip_if_py312b1 = skipIf(
+    sys.version_info == (3, 12, 0, 'beta', 1),
+    "CPython had a bug in 3.12.0b1"
+)
+
+
 class ProtocolTests(BaseTestCase):
     def test_runtime_alias(self):
         self.assertIs(runtime, runtime_checkable)
@@ -2267,10 +2273,56 @@
         del f.x
         self.assertNotIsInstance(f, HasX)
 
-    @skipIf(
-        sys.version_info == (3, 12, 0, 'beta', 1),
-        "CPython had a bug in 3.12.0b1"
-    )
+    @skip_if_py312b1
+    def test_runtime_checkable_generic_non_protocol(self):
+        # Make sure this doesn't raise AttributeError
+        with self.assertRaisesRegex(
+            TypeError,
+            "@runtime_checkable can be only applied to protocol classes",
+        ):
+            @runtime_checkable
+            class Foo(Generic[T]): ...
+
+    def test_runtime_checkable_generic(self):
+        @runtime_checkable
+        class Foo(Protocol[T]):
+            def meth(self) -> T: ...
+
+        class Impl:
+            def meth(self) -> int: ...
+
+        self.assertIsSubclass(Impl, Foo)
+
+        class NotImpl:
+            def method(self) -> int: ...
+
+        self.assertNotIsSubclass(NotImpl, Foo)
+
+    if sys.version_info >= (3, 12):
+        exec(textwrap.dedent(
+            """
+            @skip_if_py312b1
+            def test_pep695_generics_can_be_runtime_checkable(self):
+                @runtime_checkable
+                class HasX(Protocol):
+                    x: int
+
+                class Bar[T]:
+                    x: T
+                    def __init__(self, x):
+                        self.x = x
+
+                class Capybara[T]:
+                    y: str
+                    def __init__(self, y):
+                        self.y = y
+
+                self.assertIsInstance(Bar(1), HasX)
+                self.assertNotIsInstance(Capybara('a'), HasX)
+                """
+        ))
+
+    @skip_if_py312b1
     def test_protocols_isinstance_generic_classes(self):
         T = TypeVar("T")