Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #ifndef CHROME_BROWSER_SYNC_SYNCABLE_SYNCABLE_H_ | 5 #ifndef CHROME_BROWSER_SYNC_SYNCABLE_SYNCABLE_H_ |
| 6 #define CHROME_BROWSER_SYNC_SYNCABLE_SYNCABLE_H_ | 6 #define CHROME_BROWSER_SYNC_SYNCABLE_SYNCABLE_H_ |
| 7 #pragma once | 7 #pragma once |
| 8 | 8 |
| 9 #include <algorithm> | 9 #include <algorithm> |
| 10 #include <bitset> | 10 #include <bitset> |
| (...skipping 15 matching lines...) Expand all Loading... | |
| 26 #include "base/time.h" | 26 #include "base/time.h" |
| 27 #include "base/tracked.h" | 27 #include "base/tracked.h" |
| 28 #include "chrome/browser/sync/protocol/sync.pb.h" | 28 #include "chrome/browser/sync/protocol/sync.pb.h" |
| 29 #include "chrome/browser/sync/syncable/blob.h" | 29 #include "chrome/browser/sync/syncable/blob.h" |
| 30 #include "chrome/browser/sync/syncable/dir_open_result.h" | 30 #include "chrome/browser/sync/syncable/dir_open_result.h" |
| 31 #include "chrome/browser/sync/syncable/directory_event.h" | 31 #include "chrome/browser/sync/syncable/directory_event.h" |
| 32 #include "chrome/browser/sync/syncable/syncable_id.h" | 32 #include "chrome/browser/sync/syncable/syncable_id.h" |
| 33 #include "chrome/browser/sync/syncable/model_type.h" | 33 #include "chrome/browser/sync/syncable/model_type.h" |
| 34 #include "chrome/browser/sync/util/dbgq.h" | 34 #include "chrome/browser/sync/util/dbgq.h" |
| 35 #include "chrome/browser/sync/util/immutable.h" | 35 #include "chrome/browser/sync/util/immutable.h" |
| 36 #include "chrome/browser/sync/util/time.h" | |
| 36 | 37 |
| 37 struct PurgeInfo; | 38 struct PurgeInfo; |
| 38 | 39 |
| 39 namespace base { | 40 namespace base { |
| 40 class DictionaryValue; | 41 class DictionaryValue; |
| 41 class ListValue; | 42 class ListValue; |
| 42 } | 43 } |
| 43 | 44 |
| 44 namespace sync_api { | 45 namespace sync_api { |
| 45 class ReadTransaction; | 46 class ReadTransaction; |
| 46 class WriteNode; | 47 class WriteNode; |
| 47 class ReadNode; | 48 class ReadNode; |
| 48 } // sync_api | 49 } // sync_api |
| 49 | 50 |
| 50 namespace syncable { | 51 namespace syncable { |
| 51 class DirectoryChangeDelegate; | 52 class DirectoryChangeDelegate; |
| 52 class TransactionObserver; | 53 class TransactionObserver; |
| 53 class Entry; | 54 class Entry; |
| 54 | 55 |
| 55 std::ostream& operator<<(std::ostream& s, const Entry& e); | 56 std::ostream& operator<<(std::ostream& s, const Entry& e); |
| 56 | 57 |
| 57 class DirectoryBackingStore; | 58 class DirectoryBackingStore; |
| 58 | 59 |
| 59 static const int64 kInvalidMetaHandle = 0; | 60 static const int64 kInvalidMetaHandle = 0; |
| 60 | 61 |
| 61 // Update syncable_enum_conversions{.h,.cc,_unittest.cc} if you change | 62 // Things you need to update if you change any of the fields below: |
| 62 // any fields in this file. | 63 // - EntryKernel struct in syncable.h (this file) |
| 64 // - syncable_columns.h | |
| 65 // - syncable_enum_conversions{.h,.cc,_unittest.cc} | |
| 66 // - ZeroFields(), EntryKernel::ToValue(), operator<< for Entry in | |
| 67 // syncable.cc | |
| 68 // - BindFields() and UnpackEntry() in directory_backing_store.cc | |
| 69 // - TestSimpleFieldsPreservedDuringSaveChanges in syncable_unittest.cc | |
|
Nicolas Zea
2011/09/21 18:09:12
ouch.
akalin
2011/09/21 19:37:35
No kidding.
| |
| 63 | 70 |
| 64 enum { | 71 enum { |
| 65 BEGIN_FIELDS = 0, | 72 BEGIN_FIELDS = 0, |
| 66 INT64_FIELDS_BEGIN = BEGIN_FIELDS | 73 INT64_FIELDS_BEGIN = BEGIN_FIELDS |
| 67 }; | 74 }; |
| 68 | 75 |
| 69 enum MetahandleField { | 76 enum MetahandleField { |
| 70 // Primary key into the table. Keep this as a handle to the meta entry | 77 // Primary key into the table. Keep this as a handle to the meta entry |
| 71 // across transactions. | 78 // across transactions. |
| 72 META_HANDLE = INT64_FIELDS_BEGIN | 79 META_HANDLE = INT64_FIELDS_BEGIN |
| 73 }; | 80 }; |
| 74 | 81 |
| 75 enum BaseVersion { | 82 enum BaseVersion { |
| 76 // After initial upload, the version is controlled by the server, and is | 83 // After initial upload, the version is controlled by the server, and is |
| 77 // increased whenever the data or metadata changes on the server. | 84 // increased whenever the data or metadata changes on the server. |
| 78 BASE_VERSION = META_HANDLE + 1, | 85 BASE_VERSION = META_HANDLE + 1, |
| 79 }; | 86 }; |
| 80 | 87 |
| 81 enum Int64Field { | 88 enum Int64Field { |
| 82 SERVER_VERSION = BASE_VERSION + 1, | 89 SERVER_VERSION = BASE_VERSION + 1, |
| 83 MTIME, | |
| 84 SERVER_MTIME, | |
| 85 CTIME, | |
| 86 SERVER_CTIME, | |
| 87 | 90 |
| 88 // A numeric position value that indicates the relative ordering of | 91 // A numeric position value that indicates the relative ordering of |
| 89 // this object among its siblings. | 92 // this object among its siblings. |
| 90 SERVER_POSITION_IN_PARENT, | 93 SERVER_POSITION_IN_PARENT, |
| 91 | 94 |
| 92 LOCAL_EXTERNAL_ID, // ID of an item in the external local storage that this | 95 LOCAL_EXTERNAL_ID, // ID of an item in the external local storage that this |
| 93 // entry is associated with. (such as bookmarks.js) | 96 // entry is associated with. (such as bookmarks.js) |
| 94 | 97 |
| 95 INT64_FIELDS_END | 98 INT64_FIELDS_END |
| 96 }; | 99 }; |
| 97 | 100 |
| 98 enum { | 101 enum { |
| 99 INT64_FIELDS_COUNT = INT64_FIELDS_END, | 102 INT64_FIELDS_COUNT = INT64_FIELDS_END - INT64_FIELDS_BEGIN, |
| 100 ID_FIELDS_BEGIN = INT64_FIELDS_END, | 103 TIME_FIELDS_BEGIN = INT64_FIELDS_END, |
| 104 }; | |
| 105 | |
| 106 enum TimeField { | |
| 107 MTIME = TIME_FIELDS_BEGIN, | |
| 108 SERVER_MTIME, | |
| 109 CTIME, | |
| 110 SERVER_CTIME, | |
| 111 TIME_FIELDS_END, | |
| 112 }; | |
| 113 | |
| 114 enum { | |
| 115 TIME_FIELDS_COUNT = TIME_FIELDS_END - TIME_FIELDS_BEGIN, | |
| 116 ID_FIELDS_BEGIN = TIME_FIELDS_END, | |
| 101 }; | 117 }; |
| 102 | 118 |
| 103 enum IdField { | 119 enum IdField { |
| 104 // Code in InitializeTables relies on ID being the first IdField value. | 120 // Code in InitializeTables relies on ID being the first IdField value. |
| 105 ID = ID_FIELDS_BEGIN, | 121 ID = ID_FIELDS_BEGIN, |
| 106 PARENT_ID, | 122 PARENT_ID, |
| 107 SERVER_PARENT_ID, | 123 SERVER_PARENT_ID, |
| 108 | 124 |
| 109 PREV_ID, | 125 PREV_ID, |
| 110 NEXT_ID, | 126 NEXT_ID, |
| (...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 229 | 245 |
| 230 // Why the singular enums? So the code compile-time dispatches instead of | 246 // Why the singular enums? So the code compile-time dispatches instead of |
| 231 // runtime dispatches as it would with a single enum and an if() statement. | 247 // runtime dispatches as it would with a single enum and an if() statement. |
| 232 | 248 |
| 233 // The EntryKernel class contains the actual data for an entry. | 249 // The EntryKernel class contains the actual data for an entry. |
| 234 struct EntryKernel { | 250 struct EntryKernel { |
| 235 private: | 251 private: |
| 236 std::string string_fields[STRING_FIELDS_COUNT]; | 252 std::string string_fields[STRING_FIELDS_COUNT]; |
| 237 sync_pb::EntitySpecifics specifics_fields[PROTO_FIELDS_COUNT]; | 253 sync_pb::EntitySpecifics specifics_fields[PROTO_FIELDS_COUNT]; |
| 238 int64 int64_fields[INT64_FIELDS_COUNT]; | 254 int64 int64_fields[INT64_FIELDS_COUNT]; |
| 255 base::Time time_fields[TIME_FIELDS_COUNT]; | |
| 239 Id id_fields[ID_FIELDS_COUNT]; | 256 Id id_fields[ID_FIELDS_COUNT]; |
| 240 std::bitset<BIT_FIELDS_COUNT> bit_fields; | 257 std::bitset<BIT_FIELDS_COUNT> bit_fields; |
| 241 std::bitset<BIT_TEMPS_COUNT> bit_temps; | 258 std::bitset<BIT_TEMPS_COUNT> bit_temps; |
| 242 | 259 |
| 243 public: | 260 public: |
| 244 EntryKernel(); | 261 EntryKernel(); |
| 245 ~EntryKernel(); | 262 ~EntryKernel(); |
| 246 | 263 |
| 247 // Set the dirty bit, and optionally add this entry's metahandle to | 264 // Set the dirty bit, and optionally add this entry's metahandle to |
| 248 // a provided index on dirty bits in |dirty_index|. Parameter may be null, | 265 // a provided index on dirty bits in |dirty_index|. Parameter may be null, |
| (...skipping 21 matching lines...) Expand all Loading... | |
| 270 return dirty_; | 287 return dirty_; |
| 271 } | 288 } |
| 272 | 289 |
| 273 // Setters. | 290 // Setters. |
| 274 inline void put(MetahandleField field, int64 value) { | 291 inline void put(MetahandleField field, int64 value) { |
| 275 int64_fields[field - INT64_FIELDS_BEGIN] = value; | 292 int64_fields[field - INT64_FIELDS_BEGIN] = value; |
| 276 } | 293 } |
| 277 inline void put(Int64Field field, int64 value) { | 294 inline void put(Int64Field field, int64 value) { |
| 278 int64_fields[field - INT64_FIELDS_BEGIN] = value; | 295 int64_fields[field - INT64_FIELDS_BEGIN] = value; |
| 279 } | 296 } |
| 297 inline void put(TimeField field, const base::Time& value) { | |
| 298 // Round-trip to proto time format and back so that we have | |
| 299 // consistent time resolutions. | |
|
Nicolas Zea
2011/09/21 18:09:12
consistent time resolutions (in milliseconds)
akalin
2011/09/21 19:37:35
Done.
| |
| 300 time_fields[field - TIME_FIELDS_BEGIN] = | |
| 301 browser_sync::ProtoTimeToTime( | |
| 302 browser_sync::TimeToProtoTime(value)); | |
| 303 } | |
| 280 inline void put(IdField field, const Id& value) { | 304 inline void put(IdField field, const Id& value) { |
| 281 id_fields[field - ID_FIELDS_BEGIN] = value; | 305 id_fields[field - ID_FIELDS_BEGIN] = value; |
| 282 } | 306 } |
| 283 inline void put(BaseVersion field, int64 value) { | 307 inline void put(BaseVersion field, int64 value) { |
| 284 int64_fields[field - INT64_FIELDS_BEGIN] = value; | 308 int64_fields[field - INT64_FIELDS_BEGIN] = value; |
| 285 } | 309 } |
| 286 inline void put(IndexedBitField field, bool value) { | 310 inline void put(IndexedBitField field, bool value) { |
| 287 bit_fields[field - BIT_FIELDS_BEGIN] = value; | 311 bit_fields[field - BIT_FIELDS_BEGIN] = value; |
| 288 } | 312 } |
| 289 inline void put(IsDelField field, bool value) { | 313 inline void put(IsDelField field, bool value) { |
| (...skipping 12 matching lines...) Expand all Loading... | |
| 302 bit_temps[field - BIT_TEMPS_BEGIN] = value; | 326 bit_temps[field - BIT_TEMPS_BEGIN] = value; |
| 303 } | 327 } |
| 304 | 328 |
| 305 // Const ref getters. | 329 // Const ref getters. |
| 306 inline int64 ref(MetahandleField field) const { | 330 inline int64 ref(MetahandleField field) const { |
| 307 return int64_fields[field - INT64_FIELDS_BEGIN]; | 331 return int64_fields[field - INT64_FIELDS_BEGIN]; |
| 308 } | 332 } |
| 309 inline int64 ref(Int64Field field) const { | 333 inline int64 ref(Int64Field field) const { |
| 310 return int64_fields[field - INT64_FIELDS_BEGIN]; | 334 return int64_fields[field - INT64_FIELDS_BEGIN]; |
| 311 } | 335 } |
| 336 inline const base::Time& ref(TimeField field) const { | |
| 337 return time_fields[field - TIME_FIELDS_BEGIN]; | |
| 338 } | |
| 312 inline const Id& ref(IdField field) const { | 339 inline const Id& ref(IdField field) const { |
| 313 return id_fields[field - ID_FIELDS_BEGIN]; | 340 return id_fields[field - ID_FIELDS_BEGIN]; |
| 314 } | 341 } |
| 315 inline int64 ref(BaseVersion field) const { | 342 inline int64 ref(BaseVersion field) const { |
| 316 return int64_fields[field - INT64_FIELDS_BEGIN]; | 343 return int64_fields[field - INT64_FIELDS_BEGIN]; |
| 317 } | 344 } |
| 318 inline bool ref(IndexedBitField field) const { | 345 inline bool ref(IndexedBitField field) const { |
| 319 return bit_fields[field - BIT_FIELDS_BEGIN]; | 346 return bit_fields[field - BIT_FIELDS_BEGIN]; |
| 320 } | 347 } |
| 321 inline bool ref(IsDelField field) const { | 348 inline bool ref(IsDelField field) const { |
| (...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 381 return kernel_->ref(field); | 408 return kernel_->ref(field); |
| 382 } | 409 } |
| 383 inline Id Get(IdField field) const { | 410 inline Id Get(IdField field) const { |
| 384 DCHECK(kernel_); | 411 DCHECK(kernel_); |
| 385 return kernel_->ref(field); | 412 return kernel_->ref(field); |
| 386 } | 413 } |
| 387 inline int64 Get(Int64Field field) const { | 414 inline int64 Get(Int64Field field) const { |
| 388 DCHECK(kernel_); | 415 DCHECK(kernel_); |
| 389 return kernel_->ref(field); | 416 return kernel_->ref(field); |
| 390 } | 417 } |
| 418 inline const base::Time& Get(TimeField field) const { | |
| 419 DCHECK(kernel_); | |
| 420 return kernel_->ref(field); | |
| 421 } | |
| 391 inline int64 Get(BaseVersion field) const { | 422 inline int64 Get(BaseVersion field) const { |
| 392 DCHECK(kernel_); | 423 DCHECK(kernel_); |
| 393 return kernel_->ref(field); | 424 return kernel_->ref(field); |
| 394 } | 425 } |
| 395 inline bool Get(IndexedBitField field) const { | 426 inline bool Get(IndexedBitField field) const { |
| 396 DCHECK(kernel_); | 427 DCHECK(kernel_); |
| 397 return kernel_->ref(field); | 428 return kernel_->ref(field); |
| 398 } | 429 } |
| 399 inline bool Get(IsDelField field) const { | 430 inline bool Get(IsDelField field) const { |
| 400 DCHECK(kernel_); | 431 DCHECK(kernel_); |
| (...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 482 | 513 |
| 483 inline WriteTransaction* write_transaction() const { | 514 inline WriteTransaction* write_transaction() const { |
| 484 return write_transaction_; | 515 return write_transaction_; |
| 485 } | 516 } |
| 486 | 517 |
| 487 // Field Accessors. Some of them trigger the re-indexing of the entry. | 518 // Field Accessors. Some of them trigger the re-indexing of the entry. |
| 488 // Return true on success, return false on failure, which means | 519 // Return true on success, return false on failure, which means |
| 489 // that putting the value would have caused a duplicate in the index. | 520 // that putting the value would have caused a duplicate in the index. |
| 490 // TODO(chron): Remove some of these unecessary return values. | 521 // TODO(chron): Remove some of these unecessary return values. |
| 491 bool Put(Int64Field field, const int64& value); | 522 bool Put(Int64Field field, const int64& value); |
| 523 bool Put(TimeField field, const base::Time& value); | |
| 492 bool Put(IdField field, const Id& value); | 524 bool Put(IdField field, const Id& value); |
| 493 | 525 |
| 494 // Do a simple property-only update if the PARENT_ID field. Use with caution. | 526 // Do a simple property-only update if the PARENT_ID field. Use with caution. |
| 495 // | 527 // |
| 496 // The normal Put(IS_PARENT) call will move the item to the front of the | 528 // The normal Put(IS_PARENT) call will move the item to the front of the |
| 497 // sibling order to maintain the linked list invariants when the parent | 529 // sibling order to maintain the linked list invariants when the parent |
| 498 // changes. That's usually what you want to do, but it's inappropriate | 530 // changes. That's usually what you want to do, but it's inappropriate |
| 499 // when the caller is trying to change the parent ID of a the whole set | 531 // when the caller is trying to change the parent ID of a the whole set |
| 500 // of children (e.g. because the ID changed during a commit). For those | 532 // of children (e.g. because the ID changed during a commit). For those |
| 501 // cases, there's this function. It will corrupt the sibling ordering | 533 // cases, there's this function. It will corrupt the sibling ordering |
| (...skipping 674 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1176 | 1208 |
| 1177 // Only the original fields are filled in until |RecordMutations()|. | 1209 // Only the original fields are filled in until |RecordMutations()|. |
| 1178 // We use a mutation map instead of a kernel set to avoid copying. | 1210 // We use a mutation map instead of a kernel set to avoid copying. |
| 1179 EntryKernelMutationMap mutations_; | 1211 EntryKernelMutationMap mutations_; |
| 1180 | 1212 |
| 1181 DISALLOW_COPY_AND_ASSIGN(WriteTransaction); | 1213 DISALLOW_COPY_AND_ASSIGN(WriteTransaction); |
| 1182 }; | 1214 }; |
| 1183 | 1215 |
| 1184 bool IsLegalNewParent(BaseTransaction* trans, const Id& id, const Id& parentid); | 1216 bool IsLegalNewParent(BaseTransaction* trans, const Id& id, const Id& parentid); |
| 1185 | 1217 |
| 1186 int64 Now(); | |
| 1187 | |
| 1188 // This function sets only the flags needed to get this entry to sync. | 1218 // This function sets only the flags needed to get this entry to sync. |
| 1189 void MarkForSyncing(syncable::MutableEntry* e); | 1219 void MarkForSyncing(syncable::MutableEntry* e); |
| 1190 | 1220 |
| 1191 // This is not a reset. It just sets the numeric fields which are not | 1221 // This is not a reset. It just sets the numeric fields which are not |
| 1192 // initialized by the constructor to zero. | 1222 // initialized by the constructor to zero. |
| 1193 void ZeroFields(EntryKernel* entry, int first_field); | 1223 void ZeroFields(EntryKernel* entry, int first_field); |
| 1194 | 1224 |
| 1195 } // namespace syncable | 1225 } // namespace syncable |
| 1196 | 1226 |
| 1197 std::ostream& operator <<(std::ostream&, const syncable::Blob&); | 1227 std::ostream& operator <<(std::ostream&, const syncable::Blob&); |
| 1198 | 1228 |
| 1199 #endif // CHROME_BROWSER_SYNC_SYNCABLE_SYNCABLE_H_ | 1229 #endif // CHROME_BROWSER_SYNC_SYNCABLE_SYNCABLE_H_ |
| OLD | NEW |