OLD | NEW |
---|---|
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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 #include "sync/syncable/directory.h" | 5 #include "sync/syncable/directory.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 #include <iterator> | 8 #include <iterator> |
9 | 9 |
10 #include "base/base64.h" | 10 #include "base/base64.h" |
(...skipping 730 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
741 | 741 |
742 EntryKernelSet entries_to_journal; | 742 EntryKernelSet entries_to_journal; |
743 STLElementDeleter<EntryKernelSet> journal_deleter(&entries_to_journal); | 743 STLElementDeleter<EntryKernelSet> journal_deleter(&entries_to_journal); |
744 | 744 |
745 { | 745 { |
746 ScopedKernelLock lock(this); | 746 ScopedKernelLock lock(this); |
747 | 747 |
748 bool found_progress = false; | 748 bool found_progress = false; |
749 for (ModelTypeSet::Iterator iter = disabled_types.First(); iter.Good(); | 749 for (ModelTypeSet::Iterator iter = disabled_types.First(); iter.Good(); |
750 iter.Inc()) { | 750 iter.Inc()) { |
751 if (!kernel_->persisted_info.HasEmptyDownloadProgress(iter.Get())) | 751 if (!HasEmptyDownloadProgress(iter.Get())) |
752 found_progress = true; | 752 found_progress = true; |
753 } | 753 } |
754 | 754 |
755 // If none of the disabled types have progress markers, there's nothing to | 755 // If none of the disabled types have progress markers, there's nothing to |
756 // purge. | 756 // purge. |
757 if (!found_progress) | 757 if (!found_progress) |
758 return true; | 758 return true; |
759 | 759 |
760 // We iterate in two passes to avoid a bug in STLport (which is used in | 760 // We iterate in two passes to avoid a bug in STLport (which is used in |
761 // the Android build). There are some versions of that library where a | 761 // the Android build). There are some versions of that library where a |
(...skipping 156 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
918 } | 918 } |
919 | 919 |
920 void Directory::SetDownloadProgress( | 920 void Directory::SetDownloadProgress( |
921 ModelType model_type, | 921 ModelType model_type, |
922 const sync_pb::DataTypeProgressMarker& new_progress) { | 922 const sync_pb::DataTypeProgressMarker& new_progress) { |
923 ScopedKernelLock lock(this); | 923 ScopedKernelLock lock(this); |
924 kernel_->persisted_info.download_progress[model_type].CopyFrom(new_progress); | 924 kernel_->persisted_info.download_progress[model_type].CopyFrom(new_progress); |
925 kernel_->info_status = KERNEL_SHARE_INFO_DIRTY; | 925 kernel_->info_status = KERNEL_SHARE_INFO_DIRTY; |
926 } | 926 } |
927 | 927 |
928 bool Directory::HasEmptyDownloadProgress(ModelType type) const { | |
929 return kernel_->persisted_info.HasEmptyDownloadProgress(type); | |
maniscalco
2015/01/24 00:55:59
Normally, when Directory methods access kernel_ th
stanisc
2015/01/26 19:02:09
Done.
maniscalco
2015/01/26 19:17:34
Since Directory::HasEmptyDownloadProgress is calle
stanisc
2015/01/29 00:27:37
Directory::HasEmptyDownloadProgress isn't called f
maniscalco
2015/01/29 00:36:34
Ah, you're right. I misread which HasEmptyDownloa
| |
930 } | |
931 | |
928 int64 Directory::GetTransactionVersion(ModelType type) const { | 932 int64 Directory::GetTransactionVersion(ModelType type) const { |
929 kernel_->transaction_mutex.AssertAcquired(); | 933 kernel_->transaction_mutex.AssertAcquired(); |
930 return kernel_->persisted_info.transaction_version[type]; | 934 return kernel_->persisted_info.transaction_version[type]; |
931 } | 935 } |
932 | 936 |
933 void Directory::IncrementTransactionVersion(ModelType type) { | 937 void Directory::IncrementTransactionVersion(ModelType type) { |
934 kernel_->transaction_mutex.AssertAcquired(); | 938 kernel_->transaction_mutex.AssertAcquired(); |
935 kernel_->persisted_info.transaction_version[type]++; | 939 kernel_->persisted_info.transaction_version[type]++; |
936 } | 940 } |
937 | 941 |
938 void Directory::GetDataTypeContext(BaseTransaction* trans, | 942 void Directory::GetDataTypeContext(BaseTransaction* trans, |
939 ModelType type, | 943 ModelType type, |
940 sync_pb::DataTypeContext* context) const { | 944 sync_pb::DataTypeContext* context) const { |
941 ScopedKernelLock lock(this); | 945 ScopedKernelLock lock(this); |
942 context->CopyFrom(kernel_->persisted_info.datatype_context[type]); | 946 context->CopyFrom(kernel_->persisted_info.datatype_context[type]); |
943 } | 947 } |
944 | 948 |
945 void Directory::SetDataTypeContext( | 949 void Directory::SetDataTypeContext( |
946 BaseWriteTransaction* trans, | 950 BaseWriteTransaction* trans, |
947 ModelType type, | 951 ModelType type, |
948 const sync_pb::DataTypeContext& context) { | 952 const sync_pb::DataTypeContext& context) { |
949 ScopedKernelLock lock(this); | 953 ScopedKernelLock lock(this); |
950 kernel_->persisted_info.datatype_context[type].CopyFrom(context); | 954 kernel_->persisted_info.datatype_context[type].CopyFrom(context); |
951 kernel_->info_status = KERNEL_SHARE_INFO_DIRTY; | 955 kernel_->info_status = KERNEL_SHARE_INFO_DIRTY; |
952 } | 956 } |
953 | 957 |
958 // TODO: change these to not rely on the folders | |
954 ModelTypeSet Directory::InitialSyncEndedTypes() { | 959 ModelTypeSet Directory::InitialSyncEndedTypes() { |
955 syncable::ReadTransaction trans(FROM_HERE, this); | 960 syncable::ReadTransaction trans(FROM_HERE, this); |
956 ModelTypeSet protocol_types = ProtocolTypes(); | 961 ModelTypeSet protocol_types = ProtocolTypes(); |
957 ModelTypeSet initial_sync_ended_types; | 962 ModelTypeSet initial_sync_ended_types; |
958 for (ModelTypeSet::Iterator i = protocol_types.First(); i.Good(); i.Inc()) { | 963 for (ModelTypeSet::Iterator i = protocol_types.First(); i.Good(); i.Inc()) { |
959 if (InitialSyncEndedForType(&trans, i.Get())) { | 964 if (InitialSyncEndedForType(&trans, i.Get())) { |
960 initial_sync_ended_types.Put(i.Get()); | 965 initial_sync_ended_types.Put(i.Get()); |
961 } | 966 } |
962 } | 967 } |
963 return initial_sync_ended_types; | 968 return initial_sync_ended_types; |
(...skipping 204 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1168 | 1173 |
1169 if (id.IsRoot()) { | 1174 if (id.IsRoot()) { |
1170 if (!SyncAssert(e.GetIsDir(), FROM_HERE, | 1175 if (!SyncAssert(e.GetIsDir(), FROM_HERE, |
1171 "Entry should be a directory", | 1176 "Entry should be a directory", |
1172 trans)) | 1177 trans)) |
1173 return false; | 1178 return false; |
1174 if (!SyncAssert(parentid.IsRoot(), FROM_HERE, | 1179 if (!SyncAssert(parentid.IsRoot(), FROM_HERE, |
1175 "Entry should be root", | 1180 "Entry should be root", |
1176 trans)) | 1181 trans)) |
1177 return false; | 1182 return false; |
1178 if (!SyncAssert(!e.GetIsUnsynced(), FROM_HERE, | 1183 if (!SyncAssert(!e.GetIsUnsynced(), FROM_HERE, "Entry should be synced", |
1179 "Entry should be sycned", | |
1180 trans)) | 1184 trans)) |
1181 return false; | 1185 return false; |
1182 continue; | 1186 continue; |
1183 } | 1187 } |
1184 | 1188 |
1185 if (!e.GetIsDel()) { | 1189 if (!e.GetIsDel()) { |
1186 if (!SyncAssert(id != parentid, FROM_HERE, | 1190 if (!SyncAssert(id != parentid, FROM_HERE, |
1187 "Id should be different from parent id.", | 1191 "Id should be different from parent id.", |
1188 trans)) | 1192 trans)) |
1189 return false; | 1193 return false; |
1190 if (!SyncAssert(!e.GetNonUniqueName().empty(), FROM_HERE, | 1194 if (!SyncAssert(!e.GetNonUniqueName().empty(), FROM_HERE, |
1191 "Non unique name should not be empty.", | 1195 "Non unique name should not be empty.", |
1192 trans)) | 1196 trans)) |
1193 return false; | 1197 return false; |
1194 | 1198 |
1195 if (!parentid.IsNull()) { | 1199 if (!parentid.IsNull()) { |
1196 int safety_count = handles.size() + 1; | 1200 int safety_count = handles.size() + 1; |
1197 // TODO(stanisc): handle items with Null parentid | |
1198 while (!parentid.IsRoot()) { | 1201 while (!parentid.IsRoot()) { |
1199 Entry parent(trans, GET_BY_ID, parentid); | 1202 Entry parent(trans, GET_BY_ID, parentid); |
1200 if (!SyncAssert(parent.good(), FROM_HERE, | 1203 if (!SyncAssert(parent.good(), FROM_HERE, |
1201 "Parent entry is not valid.", trans)) | 1204 "Parent entry is not valid.", trans)) |
1202 return false; | 1205 return false; |
1203 if (handles.end() == handles.find(parent.GetMetahandle())) | 1206 if (handles.end() == handles.find(parent.GetMetahandle())) |
1204 break; // Skip further checking if parent was unmodified. | 1207 break; // Skip further checking if parent was unmodified. |
1205 if (!SyncAssert(parent.GetIsDir(), FROM_HERE, | 1208 if (!SyncAssert(parent.GetIsDir(), FROM_HERE, |
1206 "Parent should be a directory", trans)) | 1209 "Parent should be a directory", trans)) |
1207 return false; | 1210 return false; |
1208 if (!SyncAssert(!parent.GetIsDel(), FROM_HERE, | 1211 if (!SyncAssert(!parent.GetIsDel(), FROM_HERE, |
1209 "Parent should not have been marked for deletion.", | 1212 "Parent should not have been marked for deletion.", |
1210 trans)) | 1213 trans)) |
1211 return false; | 1214 return false; |
1212 if (!SyncAssert(handles.end() != handles.find(parent.GetMetahandle()), | 1215 if (!SyncAssert(handles.end() != handles.find(parent.GetMetahandle()), |
1213 FROM_HERE, "Parent should be in the index.", trans)) | 1216 FROM_HERE, "Parent should be in the index.", trans)) |
1214 return false; | 1217 return false; |
1215 parentid = parent.GetParentId(); | 1218 parentid = parent.GetParentId(); |
1216 if (!SyncAssert(--safety_count > 0, FROM_HERE, | 1219 if (!SyncAssert(--safety_count > 0, FROM_HERE, |
1217 "Count should be greater than zero.", trans)) | 1220 "Count should be greater than zero.", trans)) |
1218 return false; | 1221 return false; |
1219 } | 1222 } |
1220 } | 1223 } |
1221 } | 1224 } |
1222 int64 base_version = e.GetBaseVersion(); | 1225 int64 base_version = e.GetBaseVersion(); |
1223 int64 server_version = e.GetServerVersion(); | 1226 int64 server_version = e.GetServerVersion(); |
1224 bool using_unique_client_tag = !e.GetUniqueClientTag().empty(); | 1227 bool using_unique_client_tag = !e.GetUniqueClientTag().empty(); |
1228 bool is_type_root_folder = | |
1229 parentid.IsRoot() && | |
1230 e.GetUniqueServerTag() == ModelTypeToRootTag(e.GetModelType()); | |
1225 if (CHANGES_VERSION == base_version || 0 == base_version) { | 1231 if (CHANGES_VERSION == base_version || 0 == base_version) { |
1226 if (e.GetIsUnappliedUpdate()) { | 1232 if (e.GetIsUnappliedUpdate()) { |
1227 // Must be a new item, or a de-duplicated unique client tag | 1233 // Must be a new item, or a de-duplicated unique client tag |
1228 // that was created both locally and remotely. | 1234 // that was created both locally and remotely. |
1229 if (!using_unique_client_tag) { | 1235 if (!(using_unique_client_tag || is_type_root_folder)) { |
1230 if (!SyncAssert(e.GetIsDel(), FROM_HERE, | 1236 if (!SyncAssert(e.GetIsDel(), FROM_HERE, |
1231 "The entry should not have been deleted.", | 1237 "The entry should have been deleted.", |
1232 trans)) | 1238 trans)) |
1233 return false; | 1239 return false; |
1234 } | 1240 } |
1235 // It came from the server, so it must have a server ID. | 1241 // It came from the server, so it must have a server ID. |
1236 if (!SyncAssert(id.ServerKnows(), FROM_HERE, | 1242 if (!SyncAssert(id.ServerKnows(), FROM_HERE, |
1237 "The id should be from a server.", | 1243 "The id should be from a server.", |
1238 trans)) | 1244 trans)) |
1239 return false; | 1245 return false; |
1240 } else { | 1246 } else { |
1241 if (e.GetIsDir()) { | 1247 if (e.GetIsDir()) { |
1242 // TODO(chron): Implement this mode if clients ever need it. | 1248 // TODO(chron): Implement this mode if clients ever need it. |
1243 // For now, you can't combine a client tag and a directory. | 1249 // For now, you can't combine a client tag and a directory. |
1244 if (!SyncAssert(!using_unique_client_tag, FROM_HERE, | 1250 if (!SyncAssert(!using_unique_client_tag, FROM_HERE, |
1245 "Directory cannot have a client tag.", | 1251 "Directory cannot have a client tag.", |
1246 trans)) | 1252 trans)) |
1247 return false; | 1253 return false; |
1248 } | 1254 } |
1249 // Should be an uncomitted item, or a successfully deleted one. | 1255 if (is_type_root_folder) { |
1250 if (!e.GetIsDel()) { | 1256 // This must be a locally created type root folder |
1251 if (!SyncAssert(e.GetIsUnsynced(), FROM_HERE, | 1257 if (!SyncAssert( |
1252 "The item should be unsynced.", | 1258 !e.GetIsUnsynced(), FROM_HERE, |
1253 trans)) | 1259 "Locally created type root folders should not be unsynced.", |
1260 trans)) | |
1254 return false; | 1261 return false; |
1262 | |
1263 if (!SyncAssert( | |
1264 !e.GetIsDel(), FROM_HERE, | |
1265 "Locally created type root folders should not be deleted.", | |
1266 trans)) | |
1267 return false; | |
1268 } else { | |
1269 // Should be an uncomitted item, or a successfully deleted one. | |
1270 if (!e.GetIsDel()) { | |
1271 if (!SyncAssert(e.GetIsUnsynced(), FROM_HERE, | |
1272 "The item should be unsynced.", trans)) | |
1273 return false; | |
1274 } | |
1255 } | 1275 } |
1256 // If the next check failed, it would imply that an item exists | 1276 // If the next check failed, it would imply that an item exists |
1257 // on the server, isn't waiting for application locally, but either | 1277 // on the server, isn't waiting for application locally, but either |
1258 // is an unsynced create or a sucessful delete in the local copy. | 1278 // is an unsynced create or a sucessful delete in the local copy. |
1259 // Either way, that's a mismatch. | 1279 // Either way, that's a mismatch. |
1260 if (!SyncAssert(0 == server_version, FROM_HERE, | 1280 if (!SyncAssert(0 == server_version, FROM_HERE, |
1261 "Server version should be zero.", | 1281 "Server version should be zero.", |
1262 trans)) | 1282 trans)) |
1263 return false; | 1283 return false; |
1264 // Items that aren't using the unique client tag should have a zero | 1284 // Items that aren't using the unique client tag should have a zero |
(...skipping 191 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1456 void Directory::AppendChildHandles(const ScopedKernelLock& lock, | 1476 void Directory::AppendChildHandles(const ScopedKernelLock& lock, |
1457 const Id& parent_id, | 1477 const Id& parent_id, |
1458 Directory::Metahandles* result) { | 1478 Directory::Metahandles* result) { |
1459 const OrderedChildSet* children = | 1479 const OrderedChildSet* children = |
1460 kernel_->parent_child_index.GetChildren(parent_id); | 1480 kernel_->parent_child_index.GetChildren(parent_id); |
1461 if (!children) | 1481 if (!children) |
1462 return; | 1482 return; |
1463 | 1483 |
1464 for (OrderedChildSet::const_iterator i = children->begin(); | 1484 for (OrderedChildSet::const_iterator i = children->begin(); |
1465 i != children->end(); ++i) { | 1485 i != children->end(); ++i) { |
1466 DCHECK_EQ(parent_id, (*i)->ref(PARENT_ID)); | |
1467 result->push_back((*i)->ref(META_HANDLE)); | 1486 result->push_back((*i)->ref(META_HANDLE)); |
1468 } | 1487 } |
1469 } | 1488 } |
1470 | 1489 |
1471 void Directory::UnmarkDirtyEntry(WriteTransaction* trans, Entry* entry) { | 1490 void Directory::UnmarkDirtyEntry(WriteTransaction* trans, Entry* entry) { |
1472 CHECK(trans); | 1491 CHECK(trans); |
1473 entry->kernel_->clear_dirty(&kernel_->dirty_metahandles); | 1492 entry->kernel_->clear_dirty(&kernel_->dirty_metahandles); |
1474 } | 1493 } |
1475 | 1494 |
1476 void Directory::GetAttachmentIdsToUpload(BaseTransaction* trans, | 1495 void Directory::GetAttachmentIdsToUpload(BaseTransaction* trans, |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1522 // TODO(maniscalco): Eliminate redundant metadata storage (bug 415203). | 1541 // TODO(maniscalco): Eliminate redundant metadata storage (bug 415203). |
1523 std::set_difference(not_on_server_id_set.begin(), | 1542 std::set_difference(not_on_server_id_set.begin(), |
1524 not_on_server_id_set.end(), | 1543 not_on_server_id_set.end(), |
1525 on_server_id_set.begin(), | 1544 on_server_id_set.begin(), |
1526 on_server_id_set.end(), | 1545 on_server_id_set.end(), |
1527 std::inserter(*id_set, id_set->end())); | 1546 std::inserter(*id_set, id_set->end())); |
1528 } | 1547 } |
1529 | 1548 |
1530 } // namespace syncable | 1549 } // namespace syncable |
1531 } // namespace syncer | 1550 } // namespace syncer |
OLD | NEW |