1// Copyright 2015 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5// Flags: --strong-mode
6
7"use strict";
8
9function getClass() {
10  class Foo {
11    static get bar() { return 0 }
12    get bar() { return 0 }
13  }
14  return Foo;
15}
16
17function getClassExpr() {
18  return (class { static get bar() { return 0 } get bar() { return 0 } });
19}
20
21function getClassStrong() {
22  "use strong";
23  class Foo {
24    static get bar() { return 0 }
25    get bar() { return 0 }
26  }
27  return Foo;
28}
29
30function getClassExprStrong() {
31  "use strong";
32  return (class { static get bar() { return 0 } get bar() { return 0 } });
33}
34
35function addProperty(o) {
36  o.baz = 1;
37}
38
39function convertPropertyToData(o) {
40  assertTrue(o.hasOwnProperty("bar"));
41  Object.defineProperty(o, "bar", { value: 1 });
42}
43
44function testWeakClass(classFunc) {
45  assertDoesNotThrow(function(){addProperty(classFunc())});
46  assertDoesNotThrow(function(){addProperty(classFunc().prototype)});
47  assertDoesNotThrow(function(){convertPropertyToData(classFunc())});
48  assertDoesNotThrow(function(){convertPropertyToData(classFunc().prototype)});
49}
50
51function testStrongClass(classFunc) {
52  assertThrows(function(){addProperty(classFunc())}, TypeError);
53  assertThrows(function(){addProperty(classFunc().prototype)}, TypeError);
54  assertThrows(function(){convertPropertyToData(classFunc())}, TypeError);
55  assertThrows(function(){convertPropertyToData(classFunc().prototype)},
56               TypeError);
57}
58
59testWeakClass(getClass);
60testWeakClass(getClassExpr);
61
62testStrongClass(getClassStrong);
63testStrongClass(getClassExprStrong);
64
65// Check strong classes don't freeze their parents.
66(function() {
67  let parent = getClass();
68
69  let classFunc = function() {
70    "use strong";
71    class Foo extends parent {
72      static get bar() { return 0 }
73      get bar() { return 0 }
74    }
75    return Foo;
76  }
77
78  testStrongClass(classFunc);
79  assertDoesNotThrow(function(){addProperty(parent)});
80  assertDoesNotThrow(function(){convertPropertyToData(parent)});
81})();
82
83// Check strong classes don't freeze their children.
84(function() {
85  let parent = getClassStrong();
86
87  let classFunc = function() {
88    class Foo extends parent {
89      static get bar() { return 0 }
90      get bar() { return 0 }
91    }
92    return Foo;
93  }
94
95  assertThrows(function(){addProperty(parent)}, TypeError);
96  assertThrows(function(){convertPropertyToData(parent)}, TypeError);
97  testWeakClass(classFunc);
98})();
99