1/*
2 * Copyright (C) 2012 Apple Inc. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 * 1. Redistributions of source code must retain the above copyright
8 *    notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 *    notice, this list of conditions and the following disclaimer in the
11 *    documentation and/or other materials provided with the distribution.
12 *
13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 */
25
26#ifndef PropertyOffset_h
27#define PropertyOffset_h
28
29#include <wtf/StdLibExtras.h>
30
31namespace JSC {
32
33typedef int PropertyOffset;
34
35static const PropertyOffset invalidOffset = -1;
36static const PropertyOffset firstOutOfLineOffset = 100;
37
38// Declare all of the functions because they tend to do forward calls.
39inline void checkOffset(PropertyOffset);
40inline void checkOffset(PropertyOffset, int inlineCapacity);
41inline void validateOffset(PropertyOffset);
42inline void validateOffset(PropertyOffset, int inlineCapacity);
43inline bool isValidOffset(PropertyOffset);
44inline bool isInlineOffset(PropertyOffset);
45inline bool isOutOfLineOffset(PropertyOffset);
46inline size_t offsetInInlineStorage(PropertyOffset);
47inline size_t offsetInOutOfLineStorage(PropertyOffset);
48inline size_t offsetInRespectiveStorage(PropertyOffset);
49inline size_t numberOfOutOfLineSlotsForLastOffset(PropertyOffset);
50inline size_t numberOfSlotsForLastOffset(PropertyOffset, int inlineCapacity);
51
52inline void checkOffset(PropertyOffset offset)
53{
54    UNUSED_PARAM(offset);
55    ASSERT(offset >= invalidOffset);
56}
57
58inline void checkOffset(PropertyOffset offset, int inlineCapacity)
59{
60    UNUSED_PARAM(offset);
61    UNUSED_PARAM(inlineCapacity);
62    ASSERT(offset >= invalidOffset);
63    ASSERT(offset == invalidOffset
64        || offset < inlineCapacity
65        || isOutOfLineOffset(offset));
66}
67
68inline void validateOffset(PropertyOffset offset)
69{
70    checkOffset(offset);
71    ASSERT(isValidOffset(offset));
72}
73
74inline void validateOffset(PropertyOffset offset, int inlineCapacity)
75{
76    checkOffset(offset, inlineCapacity);
77    ASSERT(isValidOffset(offset));
78}
79
80inline bool isValidOffset(PropertyOffset offset)
81{
82    checkOffset(offset);
83    return offset != invalidOffset;
84}
85
86inline bool isInlineOffset(PropertyOffset offset)
87{
88    checkOffset(offset);
89    return offset < firstOutOfLineOffset;
90}
91
92inline bool isOutOfLineOffset(PropertyOffset offset)
93{
94    checkOffset(offset);
95    return !isInlineOffset(offset);
96}
97
98inline size_t offsetInInlineStorage(PropertyOffset offset)
99{
100    validateOffset(offset);
101    ASSERT(isInlineOffset(offset));
102    return offset;
103}
104
105inline size_t offsetInOutOfLineStorage(PropertyOffset offset)
106{
107    validateOffset(offset);
108    ASSERT(isOutOfLineOffset(offset));
109    return -static_cast<ptrdiff_t>(offset - firstOutOfLineOffset) - 1;
110}
111
112inline size_t offsetInRespectiveStorage(PropertyOffset offset)
113{
114    if (isInlineOffset(offset))
115        return offsetInInlineStorage(offset);
116    return offsetInOutOfLineStorage(offset);
117}
118
119inline size_t numberOfOutOfLineSlotsForLastOffset(PropertyOffset offset)
120{
121    checkOffset(offset);
122    if (offset < firstOutOfLineOffset)
123        return 0;
124    return offset - firstOutOfLineOffset + 1;
125}
126
127inline size_t numberOfSlotsForLastOffset(PropertyOffset offset, int inlineCapacity)
128{
129    checkOffset(offset, inlineCapacity);
130    if (offset < inlineCapacity)
131        return offset + 1;
132    return inlineCapacity + numberOfOutOfLineSlotsForLastOffset(offset);
133}
134
135inline PropertyOffset offsetForPropertyNumber(int propertyNumber, int inlineCapacity)
136{
137    PropertyOffset offset = propertyNumber;
138    if (offset >= inlineCapacity) {
139        offset += firstOutOfLineOffset;
140        offset -= inlineCapacity;
141    }
142    return offset;
143}
144
145} // namespace JSC
146
147#endif // PropertyOffset_h
148