Fix for browser_plugin_host_browsertest when embedder is not yet available.
[chromium-blink-merge.git] / sync / syncable / entry_kernel.h
blob562ebdb431be1aa33662ad3b63645e4459c1ebd2
1 // Copyright 2012 The Chromium 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.
5 #ifndef SYNC_SYNCABLE_ENTRY_KERNEL_H_
6 #define SYNC_SYNCABLE_ENTRY_KERNEL_H_
8 #include <set>
10 #include "base/time/time.h"
11 #include "base/values.h"
12 #include "sync/base/sync_export.h"
13 #include "sync/internal_api/public/base/model_type.h"
14 #include "sync/internal_api/public/base/unique_position.h"
15 #include "sync/internal_api/public/util/immutable.h"
16 #include "sync/protocol/sync.pb.h"
17 #include "sync/syncable/metahandle_set.h"
18 #include "sync/syncable/syncable_id.h"
19 #include "sync/util/time.h"
21 namespace syncer {
23 class Cryptographer;
25 namespace syncable {
27 // Things you need to update if you change any of the fields below:
28 // - EntryKernel struct in this file
29 // - syncable_columns.h
30 // - syncable_enum_conversions{.h,.cc,_unittest.cc}
31 // - EntryKernel::EntryKernel(), EntryKernel::ToValue() in entry_kernel.cc
32 // - operator<< in Entry.cc
33 // - BindFields() and UnpackEntry() in directory_backing_store.cc
34 // - TestSimpleFieldsPreservedDuringSaveChanges in syncable_unittest.cc
36 static const int64 kInvalidMetaHandle = 0;
38 enum {
39 BEGIN_FIELDS = 0,
40 INT64_FIELDS_BEGIN = BEGIN_FIELDS
43 enum MetahandleField {
44 // Primary key into the table. Keep this as a handle to the meta entry
45 // across transactions.
46 META_HANDLE = INT64_FIELDS_BEGIN
49 enum BaseVersion {
50 // After initial upload, the version is controlled by the server, and is
51 // increased whenever the data or metadata changes on the server.
52 BASE_VERSION = META_HANDLE + 1,
55 enum Int64Field {
56 SERVER_VERSION = BASE_VERSION + 1,
57 LOCAL_EXTERNAL_ID, // ID of an item in the external local storage that this
58 // entry is associated with. (such as bookmarks.js)
59 TRANSACTION_VERSION,
60 INT64_FIELDS_END
63 enum {
64 INT64_FIELDS_COUNT = INT64_FIELDS_END - INT64_FIELDS_BEGIN,
65 TIME_FIELDS_BEGIN = INT64_FIELDS_END,
68 enum TimeField {
69 MTIME = TIME_FIELDS_BEGIN,
70 SERVER_MTIME,
71 CTIME,
72 SERVER_CTIME,
73 TIME_FIELDS_END,
76 enum {
77 TIME_FIELDS_COUNT = TIME_FIELDS_END - TIME_FIELDS_BEGIN,
78 ID_FIELDS_BEGIN = TIME_FIELDS_END,
81 enum IdField {
82 // Code in InitializeTables relies on ID being the first IdField value.
83 ID = ID_FIELDS_BEGIN,
84 PARENT_ID,
85 SERVER_PARENT_ID,
86 ID_FIELDS_END
89 enum {
90 ID_FIELDS_COUNT = ID_FIELDS_END - ID_FIELDS_BEGIN,
91 BIT_FIELDS_BEGIN = ID_FIELDS_END
94 enum IndexedBitField {
95 IS_UNSYNCED = BIT_FIELDS_BEGIN,
96 IS_UNAPPLIED_UPDATE,
97 INDEXED_BIT_FIELDS_END,
100 enum IsDelField {
101 IS_DEL = INDEXED_BIT_FIELDS_END,
104 enum BitField {
105 IS_DIR = IS_DEL + 1,
106 SERVER_IS_DIR,
107 SERVER_IS_DEL,
108 BIT_FIELDS_END
111 enum {
112 BIT_FIELDS_COUNT = BIT_FIELDS_END - BIT_FIELDS_BEGIN,
113 STRING_FIELDS_BEGIN = BIT_FIELDS_END
116 enum StringField {
117 // Name, will be truncated by server. Can be duplicated in a folder.
118 NON_UNIQUE_NAME = STRING_FIELDS_BEGIN,
119 // The server version of |NON_UNIQUE_NAME|.
120 SERVER_NON_UNIQUE_NAME,
122 // A tag string which identifies this node as a particular top-level
123 // permanent object. The tag can be thought of as a unique key that
124 // identifies a singleton instance.
125 UNIQUE_SERVER_TAG, // Tagged by the server
126 UNIQUE_CLIENT_TAG, // Tagged by the client
127 UNIQUE_BOOKMARK_TAG, // Client tags for bookmark items
128 STRING_FIELDS_END,
131 enum {
132 STRING_FIELDS_COUNT = STRING_FIELDS_END - STRING_FIELDS_BEGIN,
133 PROTO_FIELDS_BEGIN = STRING_FIELDS_END
136 // From looking at the sqlite3 docs, it's not directly stated, but it
137 // seems the overhead for storing a NULL blob is very small.
138 enum ProtoField {
139 SPECIFICS = PROTO_FIELDS_BEGIN,
140 SERVER_SPECIFICS,
141 BASE_SERVER_SPECIFICS,
142 PROTO_FIELDS_END,
145 enum {
146 PROTO_FIELDS_COUNT = PROTO_FIELDS_END - PROTO_FIELDS_BEGIN,
147 UNIQUE_POSITION_FIELDS_BEGIN = PROTO_FIELDS_END
150 enum UniquePositionField {
151 SERVER_UNIQUE_POSITION = UNIQUE_POSITION_FIELDS_BEGIN,
152 UNIQUE_POSITION,
153 UNIQUE_POSITION_FIELDS_END
156 enum {
157 UNIQUE_POSITION_FIELDS_COUNT =
158 UNIQUE_POSITION_FIELDS_END - UNIQUE_POSITION_FIELDS_BEGIN,
159 FIELD_COUNT = UNIQUE_POSITION_FIELDS_END - BEGIN_FIELDS,
160 // Past this point we have temporaries, stored in memory only.
161 BEGIN_TEMPS = UNIQUE_POSITION_FIELDS_END,
162 BIT_TEMPS_BEGIN = BEGIN_TEMPS,
165 enum BitTemp {
166 // Not to be confused with IS_UNSYNCED, this bit is used to detect local
167 // changes to items that happen during the server Commit operation.
168 SYNCING = BIT_TEMPS_BEGIN,
169 BIT_TEMPS_END,
172 enum {
173 BIT_TEMPS_COUNT = BIT_TEMPS_END - BIT_TEMPS_BEGIN
178 struct SYNC_EXPORT_PRIVATE EntryKernel {
179 private:
180 std::string string_fields[STRING_FIELDS_COUNT];
181 sync_pb::EntitySpecifics specifics_fields[PROTO_FIELDS_COUNT];
182 int64 int64_fields[INT64_FIELDS_COUNT];
183 base::Time time_fields[TIME_FIELDS_COUNT];
184 Id id_fields[ID_FIELDS_COUNT];
185 UniquePosition unique_position_fields[UNIQUE_POSITION_FIELDS_COUNT];
186 std::bitset<BIT_FIELDS_COUNT> bit_fields;
187 std::bitset<BIT_TEMPS_COUNT> bit_temps;
189 public:
190 EntryKernel();
191 ~EntryKernel();
193 // Set the dirty bit, and optionally add this entry's metahandle to
194 // a provided index on dirty bits in |dirty_index|. Parameter may be null,
195 // and will result only in setting the dirty bit of this entry.
196 inline void mark_dirty(syncable::MetahandleSet* dirty_index) {
197 if (!dirty_ && dirty_index) {
198 DCHECK_NE(0, ref(META_HANDLE));
199 dirty_index->insert(ref(META_HANDLE));
201 dirty_ = true;
204 // Clear the dirty bit, and optionally remove this entry's metahandle from
205 // a provided index on dirty bits in |dirty_index|. Parameter may be null,
206 // and will result only in clearing dirty bit of this entry.
207 inline void clear_dirty(syncable::MetahandleSet* dirty_index) {
208 if (dirty_ && dirty_index) {
209 DCHECK_NE(0, ref(META_HANDLE));
210 dirty_index->erase(ref(META_HANDLE));
212 dirty_ = false;
215 inline bool is_dirty() const {
216 return dirty_;
219 // Setters.
220 inline void put(MetahandleField field, int64 value) {
221 int64_fields[field - INT64_FIELDS_BEGIN] = value;
223 inline void put(Int64Field field, int64 value) {
224 int64_fields[field - INT64_FIELDS_BEGIN] = value;
226 inline void put(TimeField field, const base::Time& value) {
227 // Round-trip to proto time format and back so that we have
228 // consistent time resolutions (ms).
229 time_fields[field - TIME_FIELDS_BEGIN] =
230 ProtoTimeToTime(TimeToProtoTime(value));
232 inline void put(IdField field, const Id& value) {
233 id_fields[field - ID_FIELDS_BEGIN] = value;
235 inline void put(BaseVersion field, int64 value) {
236 int64_fields[field - INT64_FIELDS_BEGIN] = value;
238 inline void put(IndexedBitField field, bool value) {
239 bit_fields[field - BIT_FIELDS_BEGIN] = value;
241 inline void put(IsDelField field, bool value) {
242 bit_fields[field - BIT_FIELDS_BEGIN] = value;
244 inline void put(BitField field, bool value) {
245 bit_fields[field - BIT_FIELDS_BEGIN] = value;
247 inline void put(StringField field, const std::string& value) {
248 string_fields[field - STRING_FIELDS_BEGIN] = value;
250 inline void put(ProtoField field, const sync_pb::EntitySpecifics& value) {
251 specifics_fields[field - PROTO_FIELDS_BEGIN].CopyFrom(value);
253 inline void put(UniquePositionField field, const UniquePosition& value) {
254 unique_position_fields[field - UNIQUE_POSITION_FIELDS_BEGIN] = value;
256 inline void put(BitTemp field, bool value) {
257 bit_temps[field - BIT_TEMPS_BEGIN] = value;
260 // Const ref getters.
261 inline int64 ref(MetahandleField field) const {
262 return int64_fields[field - INT64_FIELDS_BEGIN];
264 inline int64 ref(Int64Field field) const {
265 return int64_fields[field - INT64_FIELDS_BEGIN];
267 inline const base::Time& ref(TimeField field) const {
268 return time_fields[field - TIME_FIELDS_BEGIN];
270 inline const Id& ref(IdField field) const {
271 return id_fields[field - ID_FIELDS_BEGIN];
273 inline int64 ref(BaseVersion field) const {
274 return int64_fields[field - INT64_FIELDS_BEGIN];
276 inline bool ref(IndexedBitField field) const {
277 return bit_fields[field - BIT_FIELDS_BEGIN];
279 inline bool ref(IsDelField field) const {
280 return bit_fields[field - BIT_FIELDS_BEGIN];
282 inline bool ref(BitField field) const {
283 return bit_fields[field - BIT_FIELDS_BEGIN];
285 inline const std::string& ref(StringField field) const {
286 return string_fields[field - STRING_FIELDS_BEGIN];
288 inline const sync_pb::EntitySpecifics& ref(ProtoField field) const {
289 return specifics_fields[field - PROTO_FIELDS_BEGIN];
291 inline const UniquePosition& ref(UniquePositionField field) const {
292 return unique_position_fields[field - UNIQUE_POSITION_FIELDS_BEGIN];
294 inline bool ref(BitTemp field) const {
295 return bit_temps[field - BIT_TEMPS_BEGIN];
298 // Non-const, mutable ref getters for object types only.
299 inline std::string& mutable_ref(StringField field) {
300 return string_fields[field - STRING_FIELDS_BEGIN];
302 inline sync_pb::EntitySpecifics& mutable_ref(ProtoField field) {
303 return specifics_fields[field - PROTO_FIELDS_BEGIN];
305 inline Id& mutable_ref(IdField field) {
306 return id_fields[field - ID_FIELDS_BEGIN];
308 inline UniquePosition& mutable_ref(UniquePositionField field) {
309 return unique_position_fields[field - UNIQUE_POSITION_FIELDS_BEGIN];
312 ModelType GetModelType() const;
313 ModelType GetServerModelType() const;
314 bool ShouldMaintainPosition() const;
316 // Dumps all kernel info into a DictionaryValue and returns it.
317 // Transfers ownership of the DictionaryValue to the caller.
318 // Note: |cryptographer| is an optional parameter for use in decrypting
319 // encrypted specifics. If it is NULL or the specifics are not decryptsble,
320 // they will be serialized as empty proto's.
321 base::DictionaryValue* ToValue(Cryptographer* cryptographer) const;
323 private:
324 // Tracks whether this entry needs to be saved to the database.
325 bool dirty_;
328 class EntryKernelLessByMetaHandle {
329 public:
330 inline bool operator()(const EntryKernel* a,
331 const EntryKernel* b) const {
332 return a->ref(META_HANDLE) < b->ref(META_HANDLE);
336 typedef std::set<const EntryKernel*, EntryKernelLessByMetaHandle>
337 EntryKernelSet;
339 struct EntryKernelMutation {
340 EntryKernel original, mutated;
343 typedef std::map<int64, EntryKernelMutation> EntryKernelMutationMap;
345 typedef Immutable<EntryKernelMutationMap> ImmutableEntryKernelMutationMap;
347 // Caller owns the return value.
348 base::DictionaryValue* EntryKernelMutationToValue(
349 const EntryKernelMutation& mutation);
351 // Caller owns the return value.
352 base::ListValue* EntryKernelMutationMapToValue(
353 const EntryKernelMutationMap& mutations);
355 } // namespace syncable
356 } // namespace syncer
358 #endif // SYNC_SYNCABLE_ENTRY_KERNEL_H_