Fossil SCM

Merge in the experimental clone speed enhancement.

drh 2010-12-14 00:36 trunk merge
Commit 3543ed62bb937b7a983613c23f4c7375fcc293bf
+3 -3
--- src/attach.c
+++ src/attach.c
@@ -241,11 +241,11 @@
241241
int rid;
242242
int i, n;
243243
244244
db_begin_transaction();
245245
blob_init(&content, aContent, szContent);
246
- rid = content_put(&content, 0, 0);
246
+ rid = content_put(&content, 0, 0, 0);
247247
zUUID = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
248248
blob_zero(&manifest);
249249
for(i=n=0; zName[i]; i++){
250250
if( zName[i]=='/' || zName[i]=='\\' ) n = i;
251251
}
@@ -263,11 +263,11 @@
263263
zDate[10] = 'T';
264264
blob_appendf(&manifest, "D %s\n", zDate);
265265
blob_appendf(&manifest, "U %F\n", g.zLogin ? g.zLogin : "nobody");
266266
md5sum_blob(&manifest, &cksum);
267267
blob_appendf(&manifest, "Z %b\n", &cksum);
268
- rid = content_put(&manifest, 0, 0);
268
+ rid = content_put(&manifest, 0, 0, 0);
269269
manifest_crosslink(rid, &manifest);
270270
db_end_transaction(0);
271271
cgi_redirect(zFrom);
272272
}
273273
style_header("Add Attachment");
@@ -343,11 +343,11 @@
343343
zDate[10] = 'T';
344344
blob_appendf(&manifest, "D %s\n", zDate);
345345
blob_appendf(&manifest, "U %F\n", g.zLogin ? g.zLogin : "nobody");
346346
md5sum_blob(&manifest, &cksum);
347347
blob_appendf(&manifest, "Z %b\n", &cksum);
348
- rid = content_put(&manifest, 0, 0);
348
+ rid = content_put(&manifest, 0, 0, 0);
349349
manifest_crosslink(rid, &manifest);
350350
db_end_transaction(0);
351351
cgi_redirect(zFrom);
352352
}
353353
style_header("Delete Attachment");
354354
--- src/attach.c
+++ src/attach.c
@@ -241,11 +241,11 @@
241 int rid;
242 int i, n;
243
244 db_begin_transaction();
245 blob_init(&content, aContent, szContent);
246 rid = content_put(&content, 0, 0);
247 zUUID = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
248 blob_zero(&manifest);
249 for(i=n=0; zName[i]; i++){
250 if( zName[i]=='/' || zName[i]=='\\' ) n = i;
251 }
@@ -263,11 +263,11 @@
263 zDate[10] = 'T';
264 blob_appendf(&manifest, "D %s\n", zDate);
265 blob_appendf(&manifest, "U %F\n", g.zLogin ? g.zLogin : "nobody");
266 md5sum_blob(&manifest, &cksum);
267 blob_appendf(&manifest, "Z %b\n", &cksum);
268 rid = content_put(&manifest, 0, 0);
269 manifest_crosslink(rid, &manifest);
270 db_end_transaction(0);
271 cgi_redirect(zFrom);
272 }
273 style_header("Add Attachment");
@@ -343,11 +343,11 @@
343 zDate[10] = 'T';
344 blob_appendf(&manifest, "D %s\n", zDate);
345 blob_appendf(&manifest, "U %F\n", g.zLogin ? g.zLogin : "nobody");
346 md5sum_blob(&manifest, &cksum);
347 blob_appendf(&manifest, "Z %b\n", &cksum);
348 rid = content_put(&manifest, 0, 0);
349 manifest_crosslink(rid, &manifest);
350 db_end_transaction(0);
351 cgi_redirect(zFrom);
352 }
353 style_header("Delete Attachment");
354
--- src/attach.c
+++ src/attach.c
@@ -241,11 +241,11 @@
241 int rid;
242 int i, n;
243
244 db_begin_transaction();
245 blob_init(&content, aContent, szContent);
246 rid = content_put(&content, 0, 0, 0);
247 zUUID = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
248 blob_zero(&manifest);
249 for(i=n=0; zName[i]; i++){
250 if( zName[i]=='/' || zName[i]=='\\' ) n = i;
251 }
@@ -263,11 +263,11 @@
263 zDate[10] = 'T';
264 blob_appendf(&manifest, "D %s\n", zDate);
265 blob_appendf(&manifest, "U %F\n", g.zLogin ? g.zLogin : "nobody");
266 md5sum_blob(&manifest, &cksum);
267 blob_appendf(&manifest, "Z %b\n", &cksum);
268 rid = content_put(&manifest, 0, 0, 0);
269 manifest_crosslink(rid, &manifest);
270 db_end_transaction(0);
271 cgi_redirect(zFrom);
272 }
273 style_header("Add Attachment");
@@ -343,11 +343,11 @@
343 zDate[10] = 'T';
344 blob_appendf(&manifest, "D %s\n", zDate);
345 blob_appendf(&manifest, "U %F\n", g.zLogin ? g.zLogin : "nobody");
346 md5sum_blob(&manifest, &cksum);
347 blob_appendf(&manifest, "Z %b\n", &cksum);
348 rid = content_put(&manifest, 0, 0, 0);
349 manifest_crosslink(rid, &manifest);
350 db_end_transaction(0);
351 cgi_redirect(zFrom);
352 }
353 style_header("Delete Attachment");
354
+1 -1
--- src/branch.c
+++ src/branch.c
@@ -137,11 +137,11 @@
137137
db_end_transaction(1);
138138
fossil_exit(1);
139139
}
140140
}
141141
142
- brid = content_put(&branch, 0, 0);
142
+ brid = content_put(&branch, 0, 0, 0);
143143
if( brid==0 ){
144144
fossil_panic("trouble committing manifest: %s", g.zErrMsg);
145145
}
146146
db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", brid);
147147
if( manifest_crosslink(brid, &branch)==0 ){
148148
--- src/branch.c
+++ src/branch.c
@@ -137,11 +137,11 @@
137 db_end_transaction(1);
138 fossil_exit(1);
139 }
140 }
141
142 brid = content_put(&branch, 0, 0);
143 if( brid==0 ){
144 fossil_panic("trouble committing manifest: %s", g.zErrMsg);
145 }
146 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", brid);
147 if( manifest_crosslink(brid, &branch)==0 ){
148
--- src/branch.c
+++ src/branch.c
@@ -137,11 +137,11 @@
137 db_end_transaction(1);
138 fossil_exit(1);
139 }
140 }
141
142 brid = content_put(&branch, 0, 0, 0);
143 if( brid==0 ){
144 fossil_panic("trouble committing manifest: %s", g.zErrMsg);
145 }
146 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", brid);
147 if( manifest_crosslink(brid, &branch)==0 ){
148
+2 -2
--- src/checkin.c
+++ src/checkin.c
@@ -965,11 +965,11 @@
965965
zFullname = db_column_text(&q, 1);
966966
rid = db_column_int(&q, 2);
967967
968968
blob_zero(&content);
969969
blob_read_from_file(&content, zFullname);
970
- nrid = content_put(&content, 0, 0);
970
+ nrid = content_put(&content, 0, 0, 0);
971971
blob_reset(&content);
972972
if( rid>0 ){
973973
content_deltify(rid, nrid, 0);
974974
}
975975
db_multi_exec("UPDATE vfile SET mrid=%d, rid=%d WHERE id=%d", nrid,nrid,id);
@@ -1057,11 +1057,11 @@
10571057
blob_write_to_file(&manifest, zManifestFile);
10581058
blob_reset(&manifest);
10591059
blob_read_from_file(&manifest, zManifestFile);
10601060
free(zManifestFile);
10611061
}
1062
- nvid = content_put(&manifest, 0, 0);
1062
+ nvid = content_put(&manifest, 0, 0, 0);
10631063
if( nvid==0 ){
10641064
fossil_panic("trouble committing manifest: %s", g.zErrMsg);
10651065
}
10661066
db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nvid);
10671067
manifest_crosslink(nvid, &manifest);
10681068
--- src/checkin.c
+++ src/checkin.c
@@ -965,11 +965,11 @@
965 zFullname = db_column_text(&q, 1);
966 rid = db_column_int(&q, 2);
967
968 blob_zero(&content);
969 blob_read_from_file(&content, zFullname);
970 nrid = content_put(&content, 0, 0);
971 blob_reset(&content);
972 if( rid>0 ){
973 content_deltify(rid, nrid, 0);
974 }
975 db_multi_exec("UPDATE vfile SET mrid=%d, rid=%d WHERE id=%d", nrid,nrid,id);
@@ -1057,11 +1057,11 @@
1057 blob_write_to_file(&manifest, zManifestFile);
1058 blob_reset(&manifest);
1059 blob_read_from_file(&manifest, zManifestFile);
1060 free(zManifestFile);
1061 }
1062 nvid = content_put(&manifest, 0, 0);
1063 if( nvid==0 ){
1064 fossil_panic("trouble committing manifest: %s", g.zErrMsg);
1065 }
1066 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nvid);
1067 manifest_crosslink(nvid, &manifest);
1068
--- src/checkin.c
+++ src/checkin.c
@@ -965,11 +965,11 @@
965 zFullname = db_column_text(&q, 1);
966 rid = db_column_int(&q, 2);
967
968 blob_zero(&content);
969 blob_read_from_file(&content, zFullname);
970 nrid = content_put(&content, 0, 0, 0);
971 blob_reset(&content);
972 if( rid>0 ){
973 content_deltify(rid, nrid, 0);
974 }
975 db_multi_exec("UPDATE vfile SET mrid=%d, rid=%d WHERE id=%d", nrid,nrid,id);
@@ -1057,11 +1057,11 @@
1057 blob_write_to_file(&manifest, zManifestFile);
1058 blob_reset(&manifest);
1059 blob_read_from_file(&manifest, zManifestFile);
1060 free(zManifestFile);
1061 }
1062 nvid = content_put(&manifest, 0, 0, 0);
1063 if( nvid==0 ){
1064 fossil_panic("trouble committing manifest: %s", g.zErrMsg);
1065 }
1066 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nvid);
1067 manifest_crosslink(nvid, &manifest);
1068
+2 -2
--- src/checkin.c
+++ src/checkin.c
@@ -965,11 +965,11 @@
965965
zFullname = db_column_text(&q, 1);
966966
rid = db_column_int(&q, 2);
967967
968968
blob_zero(&content);
969969
blob_read_from_file(&content, zFullname);
970
- nrid = content_put(&content, 0, 0);
970
+ nrid = content_put(&content, 0, 0, 0);
971971
blob_reset(&content);
972972
if( rid>0 ){
973973
content_deltify(rid, nrid, 0);
974974
}
975975
db_multi_exec("UPDATE vfile SET mrid=%d, rid=%d WHERE id=%d", nrid,nrid,id);
@@ -1057,11 +1057,11 @@
10571057
blob_write_to_file(&manifest, zManifestFile);
10581058
blob_reset(&manifest);
10591059
blob_read_from_file(&manifest, zManifestFile);
10601060
free(zManifestFile);
10611061
}
1062
- nvid = content_put(&manifest, 0, 0);
1062
+ nvid = content_put(&manifest, 0, 0, 0);
10631063
if( nvid==0 ){
10641064
fossil_panic("trouble committing manifest: %s", g.zErrMsg);
10651065
}
10661066
db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nvid);
10671067
manifest_crosslink(nvid, &manifest);
10681068
--- src/checkin.c
+++ src/checkin.c
@@ -965,11 +965,11 @@
965 zFullname = db_column_text(&q, 1);
966 rid = db_column_int(&q, 2);
967
968 blob_zero(&content);
969 blob_read_from_file(&content, zFullname);
970 nrid = content_put(&content, 0, 0);
971 blob_reset(&content);
972 if( rid>0 ){
973 content_deltify(rid, nrid, 0);
974 }
975 db_multi_exec("UPDATE vfile SET mrid=%d, rid=%d WHERE id=%d", nrid,nrid,id);
@@ -1057,11 +1057,11 @@
1057 blob_write_to_file(&manifest, zManifestFile);
1058 blob_reset(&manifest);
1059 blob_read_from_file(&manifest, zManifestFile);
1060 free(zManifestFile);
1061 }
1062 nvid = content_put(&manifest, 0, 0);
1063 if( nvid==0 ){
1064 fossil_panic("trouble committing manifest: %s", g.zErrMsg);
1065 }
1066 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nvid);
1067 manifest_crosslink(nvid, &manifest);
1068
--- src/checkin.c
+++ src/checkin.c
@@ -965,11 +965,11 @@
965 zFullname = db_column_text(&q, 1);
966 rid = db_column_int(&q, 2);
967
968 blob_zero(&content);
969 blob_read_from_file(&content, zFullname);
970 nrid = content_put(&content, 0, 0, 0);
971 blob_reset(&content);
972 if( rid>0 ){
973 content_deltify(rid, nrid, 0);
974 }
975 db_multi_exec("UPDATE vfile SET mrid=%d, rid=%d WHERE id=%d", nrid,nrid,id);
@@ -1057,11 +1057,11 @@
1057 blob_write_to_file(&manifest, zManifestFile);
1058 blob_reset(&manifest);
1059 blob_read_from_file(&manifest, zManifestFile);
1060 free(zManifestFile);
1061 }
1062 nvid = content_put(&manifest, 0, 0, 0);
1063 if( nvid==0 ){
1064 fossil_panic("trouble committing manifest: %s", g.zErrMsg);
1065 }
1066 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nvid);
1067 manifest_crosslink(nvid, &manifest);
1068
+14 -7
--- src/content.c
+++ src/content.c
@@ -421,20 +421,22 @@
421421
/*
422422
** Write content into the database. Return the record ID. If the
423423
** content is already in the database, just return the record ID.
424424
**
425425
** If srcId is specified, then pBlob is delta content from
426
-** the srcId record. srcId might be a phantom.
426
+** the srcId record. srcId might be a phantom. If nBlob>0 then the
427
+** pBlob value has already been compressed and nBlob is its uncompressed
428
+** size. If nBlob>0 then zUuid must be valid.
427429
**
428430
** zUuid is the UUID of the artifact, if it is specified. When srcId is
429431
** specified then zUuid must always be specified. If srcId is zero,
430432
** and zUuid is zero then the correct zUuid is computed from pBlob.
431433
**
432434
** If the record already exists but is a phantom, the pBlob content
433435
** is inserted and the phatom becomes a real record.
434436
*/
435
-int content_put(Blob *pBlob, const char *zUuid, int srcId){
437
+int content_put(Blob *pBlob, const char *zUuid, int srcId, int nBlob){
436438
int size;
437439
int rid;
438440
Stmt s1;
439441
Blob cmpr;
440442
Blob hash;
@@ -444,15 +446,16 @@
444446
assert( g.repositoryOpen );
445447
assert( pBlob!=0 );
446448
assert( srcId==0 || zUuid!=0 );
447449
if( zUuid==0 ){
448450
assert( pBlob!=0 );
451
+ assert( nBlob==0 );
449452
sha1sum_blob(pBlob, &hash);
450453
}else{
451454
blob_init(&hash, zUuid, -1);
452455
}
453
- size = blob_size(pBlob);
456
+ size = nBlob ? nBlob : blob_size(pBlob);
454457
db_begin_transaction();
455458
456459
/* Check to see if the entry already exists and if it does whether
457460
** or not the entry is a phantom
458461
*/
@@ -481,11 +484,15 @@
481484
g.userUid, g.zNonce, g.zIpAddr
482485
);
483486
g.rcvid = db_last_insert_rowid();
484487
}
485488
486
- blob_compress(pBlob, &cmpr);
489
+ if( nBlob ){
490
+ cmpr = pBlob[0];
491
+ }else{
492
+ blob_compress(pBlob, &cmpr);
493
+ }
487494
if( rid>0 ){
488495
/* We are just adding data to a phantom */
489496
db_prepare(&s1,
490497
"UPDATE blob SET rcvid=%d, size=%d, content=:data WHERE rid=%d",
491498
g.rcvid, size, rid
@@ -513,11 +520,11 @@
513520
if( g.markPrivate ){
514521
db_multi_exec("INSERT INTO private VALUES(%d)", rid);
515522
markAsUnclustered = 0;
516523
}
517524
}
518
- blob_reset(&cmpr);
525
+ if( nBlob==0 ) blob_reset(&cmpr);
519526
520527
/* If the srcId is specified, then the data we just added is
521528
** really a delta. Record this fact in the delta table.
522529
*/
523530
if( srcId ){
@@ -590,20 +597,20 @@
590597
591598
592599
/*
593600
** COMMAND: test-content-put
594601
**
595
-** Extract a blob from the database and write it into a file.
602
+** Extract a blob from a file and write it into the database
596603
*/
597604
void test_content_put_cmd(void){
598605
int rid;
599606
Blob content;
600607
if( g.argc!=3 ) usage("FILENAME");
601608
db_must_be_within_tree();
602609
user_select();
603610
blob_read_from_file(&content, g.argv[2]);
604
- rid = content_put(&content, 0, 0);
611
+ rid = content_put(&content, 0, 0, 0);
605612
printf("inserted as record %d\n", rid);
606613
}
607614
608615
/*
609616
** Make sure the content at rid is the original content and is not a
610617
--- src/content.c
+++ src/content.c
@@ -421,20 +421,22 @@
421 /*
422 ** Write content into the database. Return the record ID. If the
423 ** content is already in the database, just return the record ID.
424 **
425 ** If srcId is specified, then pBlob is delta content from
426 ** the srcId record. srcId might be a phantom.
 
 
427 **
428 ** zUuid is the UUID of the artifact, if it is specified. When srcId is
429 ** specified then zUuid must always be specified. If srcId is zero,
430 ** and zUuid is zero then the correct zUuid is computed from pBlob.
431 **
432 ** If the record already exists but is a phantom, the pBlob content
433 ** is inserted and the phatom becomes a real record.
434 */
435 int content_put(Blob *pBlob, const char *zUuid, int srcId){
436 int size;
437 int rid;
438 Stmt s1;
439 Blob cmpr;
440 Blob hash;
@@ -444,15 +446,16 @@
444 assert( g.repositoryOpen );
445 assert( pBlob!=0 );
446 assert( srcId==0 || zUuid!=0 );
447 if( zUuid==0 ){
448 assert( pBlob!=0 );
 
449 sha1sum_blob(pBlob, &hash);
450 }else{
451 blob_init(&hash, zUuid, -1);
452 }
453 size = blob_size(pBlob);
454 db_begin_transaction();
455
456 /* Check to see if the entry already exists and if it does whether
457 ** or not the entry is a phantom
458 */
@@ -481,11 +484,15 @@
481 g.userUid, g.zNonce, g.zIpAddr
482 );
483 g.rcvid = db_last_insert_rowid();
484 }
485
486 blob_compress(pBlob, &cmpr);
 
 
 
 
487 if( rid>0 ){
488 /* We are just adding data to a phantom */
489 db_prepare(&s1,
490 "UPDATE blob SET rcvid=%d, size=%d, content=:data WHERE rid=%d",
491 g.rcvid, size, rid
@@ -513,11 +520,11 @@
513 if( g.markPrivate ){
514 db_multi_exec("INSERT INTO private VALUES(%d)", rid);
515 markAsUnclustered = 0;
516 }
517 }
518 blob_reset(&cmpr);
519
520 /* If the srcId is specified, then the data we just added is
521 ** really a delta. Record this fact in the delta table.
522 */
523 if( srcId ){
@@ -590,20 +597,20 @@
590
591
592 /*
593 ** COMMAND: test-content-put
594 **
595 ** Extract a blob from the database and write it into a file.
596 */
597 void test_content_put_cmd(void){
598 int rid;
599 Blob content;
600 if( g.argc!=3 ) usage("FILENAME");
601 db_must_be_within_tree();
602 user_select();
603 blob_read_from_file(&content, g.argv[2]);
604 rid = content_put(&content, 0, 0);
605 printf("inserted as record %d\n", rid);
606 }
607
608 /*
609 ** Make sure the content at rid is the original content and is not a
610
--- src/content.c
+++ src/content.c
@@ -421,20 +421,22 @@
421 /*
422 ** Write content into the database. Return the record ID. If the
423 ** content is already in the database, just return the record ID.
424 **
425 ** If srcId is specified, then pBlob is delta content from
426 ** the srcId record. srcId might be a phantom. If nBlob>0 then the
427 ** pBlob value has already been compressed and nBlob is its uncompressed
428 ** size. If nBlob>0 then zUuid must be valid.
429 **
430 ** zUuid is the UUID of the artifact, if it is specified. When srcId is
431 ** specified then zUuid must always be specified. If srcId is zero,
432 ** and zUuid is zero then the correct zUuid is computed from pBlob.
433 **
434 ** If the record already exists but is a phantom, the pBlob content
435 ** is inserted and the phatom becomes a real record.
436 */
437 int content_put(Blob *pBlob, const char *zUuid, int srcId, int nBlob){
438 int size;
439 int rid;
440 Stmt s1;
441 Blob cmpr;
442 Blob hash;
@@ -444,15 +446,16 @@
446 assert( g.repositoryOpen );
447 assert( pBlob!=0 );
448 assert( srcId==0 || zUuid!=0 );
449 if( zUuid==0 ){
450 assert( pBlob!=0 );
451 assert( nBlob==0 );
452 sha1sum_blob(pBlob, &hash);
453 }else{
454 blob_init(&hash, zUuid, -1);
455 }
456 size = nBlob ? nBlob : blob_size(pBlob);
457 db_begin_transaction();
458
459 /* Check to see if the entry already exists and if it does whether
460 ** or not the entry is a phantom
461 */
@@ -481,11 +484,15 @@
484 g.userUid, g.zNonce, g.zIpAddr
485 );
486 g.rcvid = db_last_insert_rowid();
487 }
488
489 if( nBlob ){
490 cmpr = pBlob[0];
491 }else{
492 blob_compress(pBlob, &cmpr);
493 }
494 if( rid>0 ){
495 /* We are just adding data to a phantom */
496 db_prepare(&s1,
497 "UPDATE blob SET rcvid=%d, size=%d, content=:data WHERE rid=%d",
498 g.rcvid, size, rid
@@ -513,11 +520,11 @@
520 if( g.markPrivate ){
521 db_multi_exec("INSERT INTO private VALUES(%d)", rid);
522 markAsUnclustered = 0;
523 }
524 }
525 if( nBlob==0 ) blob_reset(&cmpr);
526
527 /* If the srcId is specified, then the data we just added is
528 ** really a delta. Record this fact in the delta table.
529 */
530 if( srcId ){
@@ -590,20 +597,20 @@
597
598
599 /*
600 ** COMMAND: test-content-put
601 **
602 ** Extract a blob from a file and write it into the database
603 */
604 void test_content_put_cmd(void){
605 int rid;
606 Blob content;
607 if( g.argc!=3 ) usage("FILENAME");
608 db_must_be_within_tree();
609 user_select();
610 blob_read_from_file(&content, g.argv[2]);
611 rid = content_put(&content, 0, 0, 0);
612 printf("inserted as record %d\n", rid);
613 }
614
615 /*
616 ** Make sure the content at rid is the original content and is not a
617
+4 -1
--- src/db.c
+++ src/db.c
@@ -357,10 +357,13 @@
357357
return sqlite3_column_double(pStmt->pStmt, N);
358358
}
359359
const char *db_column_text(Stmt *pStmt, int N){
360360
return (char*)sqlite3_column_text(pStmt->pStmt, N);
361361
}
362
+const char *db_column_raw(Stmt *pStmt, int N){
363
+ return (const char*)sqlite3_column_blob(pStmt->pStmt, N);
364
+}
362365
const char *db_column_name(Stmt *pStmt, int N){
363366
return (char*)sqlite3_column_name(pStmt->pStmt, N);
364367
}
365368
int db_column_count(Stmt *pStmt){
366369
return sqlite3_column_count(pStmt->pStmt);
@@ -1053,11 +1056,11 @@
10531056
blob_appendf(&manifest, "T *sym-trunk *\n");
10541057
blob_appendf(&manifest, "U %F\n", g.zLogin);
10551058
md5sum_blob(&manifest, &hash);
10561059
blob_appendf(&manifest, "Z %b\n", &hash);
10571060
blob_reset(&hash);
1058
- rid = content_put(&manifest, 0, 0);
1061
+ rid = content_put(&manifest, 0, 0, 0);
10591062
manifest_crosslink(rid, &manifest);
10601063
}
10611064
}
10621065
10631066
/*
10641067
--- src/db.c
+++ src/db.c
@@ -357,10 +357,13 @@
357 return sqlite3_column_double(pStmt->pStmt, N);
358 }
359 const char *db_column_text(Stmt *pStmt, int N){
360 return (char*)sqlite3_column_text(pStmt->pStmt, N);
361 }
 
 
 
362 const char *db_column_name(Stmt *pStmt, int N){
363 return (char*)sqlite3_column_name(pStmt->pStmt, N);
364 }
365 int db_column_count(Stmt *pStmt){
366 return sqlite3_column_count(pStmt->pStmt);
@@ -1053,11 +1056,11 @@
1053 blob_appendf(&manifest, "T *sym-trunk *\n");
1054 blob_appendf(&manifest, "U %F\n", g.zLogin);
1055 md5sum_blob(&manifest, &hash);
1056 blob_appendf(&manifest, "Z %b\n", &hash);
1057 blob_reset(&hash);
1058 rid = content_put(&manifest, 0, 0);
1059 manifest_crosslink(rid, &manifest);
1060 }
1061 }
1062
1063 /*
1064
--- src/db.c
+++ src/db.c
@@ -357,10 +357,13 @@
357 return sqlite3_column_double(pStmt->pStmt, N);
358 }
359 const char *db_column_text(Stmt *pStmt, int N){
360 return (char*)sqlite3_column_text(pStmt->pStmt, N);
361 }
362 const char *db_column_raw(Stmt *pStmt, int N){
363 return (const char*)sqlite3_column_blob(pStmt->pStmt, N);
364 }
365 const char *db_column_name(Stmt *pStmt, int N){
366 return (char*)sqlite3_column_name(pStmt->pStmt, N);
367 }
368 int db_column_count(Stmt *pStmt){
369 return sqlite3_column_count(pStmt->pStmt);
@@ -1053,11 +1056,11 @@
1056 blob_appendf(&manifest, "T *sym-trunk *\n");
1057 blob_appendf(&manifest, "U %F\n", g.zLogin);
1058 md5sum_blob(&manifest, &hash);
1059 blob_appendf(&manifest, "Z %b\n", &hash);
1060 blob_reset(&hash);
1061 rid = content_put(&manifest, 0, 0, 0);
1062 manifest_crosslink(rid, &manifest);
1063 }
1064 }
1065
1066 /*
1067
+1 -1
--- src/event.c
+++ src/event.c
@@ -344,11 +344,11 @@
344344
}
345345
blob_appendf(&event, "W %d\n%s\n", strlen(zBody), zBody);
346346
md5sum_blob(&event, &cksum);
347347
blob_appendf(&event, "Z %b\n", &cksum);
348348
blob_reset(&cksum);
349
- nrid = content_put(&event, 0, 0);
349
+ nrid = content_put(&event, 0, 0, 0);
350350
db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
351351
manifest_crosslink(nrid, &event);
352352
blob_reset(&event);
353353
content_deltify(rid, nrid, 0);
354354
db_end_transaction(0);
355355
--- src/event.c
+++ src/event.c
@@ -344,11 +344,11 @@
344 }
345 blob_appendf(&event, "W %d\n%s\n", strlen(zBody), zBody);
346 md5sum_blob(&event, &cksum);
347 blob_appendf(&event, "Z %b\n", &cksum);
348 blob_reset(&cksum);
349 nrid = content_put(&event, 0, 0);
350 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
351 manifest_crosslink(nrid, &event);
352 blob_reset(&event);
353 content_deltify(rid, nrid, 0);
354 db_end_transaction(0);
355
--- src/event.c
+++ src/event.c
@@ -344,11 +344,11 @@
344 }
345 blob_appendf(&event, "W %d\n%s\n", strlen(zBody), zBody);
346 md5sum_blob(&event, &cksum);
347 blob_appendf(&event, "Z %b\n", &cksum);
348 blob_reset(&cksum);
349 nrid = content_put(&event, 0, 0, 0);
350 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
351 manifest_crosslink(nrid, &event);
352 blob_reset(&event);
353 content_deltify(rid, nrid, 0);
354 db_end_transaction(0);
355
+1 -1
--- src/info.c
+++ src/info.c
@@ -1519,11 +1519,11 @@
15191519
blob_appendf(&ctrl, "U %F\n", g.zLogin);
15201520
md5sum_blob(&ctrl, &cksum);
15211521
blob_appendf(&ctrl, "Z %b\n", &cksum);
15221522
db_begin_transaction();
15231523
g.markPrivate = content_is_private(rid);
1524
- nrid = content_put(&ctrl, 0, 0);
1524
+ nrid = content_put(&ctrl, 0, 0, 0);
15251525
manifest_crosslink(nrid, &ctrl);
15261526
db_end_transaction(0);
15271527
}
15281528
cgi_redirectf("ci?name=%s", zUuid);
15291529
}
15301530
--- src/info.c
+++ src/info.c
@@ -1519,11 +1519,11 @@
1519 blob_appendf(&ctrl, "U %F\n", g.zLogin);
1520 md5sum_blob(&ctrl, &cksum);
1521 blob_appendf(&ctrl, "Z %b\n", &cksum);
1522 db_begin_transaction();
1523 g.markPrivate = content_is_private(rid);
1524 nrid = content_put(&ctrl, 0, 0);
1525 manifest_crosslink(nrid, &ctrl);
1526 db_end_transaction(0);
1527 }
1528 cgi_redirectf("ci?name=%s", zUuid);
1529 }
1530
--- src/info.c
+++ src/info.c
@@ -1519,11 +1519,11 @@
1519 blob_appendf(&ctrl, "U %F\n", g.zLogin);
1520 md5sum_blob(&ctrl, &cksum);
1521 blob_appendf(&ctrl, "Z %b\n", &cksum);
1522 db_begin_transaction();
1523 g.markPrivate = content_is_private(rid);
1524 nrid = content_put(&ctrl, 0, 0, 0);
1525 manifest_crosslink(nrid, &ctrl);
1526 db_end_transaction(0);
1527 }
1528 cgi_redirectf("ci?name=%s", zUuid);
1529 }
1530
+1 -1
--- src/info.c
+++ src/info.c
@@ -1519,11 +1519,11 @@
15191519
blob_appendf(&ctrl, "U %F\n", g.zLogin);
15201520
md5sum_blob(&ctrl, &cksum);
15211521
blob_appendf(&ctrl, "Z %b\n", &cksum);
15221522
db_begin_transaction();
15231523
g.markPrivate = content_is_private(rid);
1524
- nrid = content_put(&ctrl, 0, 0);
1524
+ nrid = content_put(&ctrl, 0, 0, 0);
15251525
manifest_crosslink(nrid, &ctrl);
15261526
db_end_transaction(0);
15271527
}
15281528
cgi_redirectf("ci?name=%s", zUuid);
15291529
}
15301530
--- src/info.c
+++ src/info.c
@@ -1519,11 +1519,11 @@
1519 blob_appendf(&ctrl, "U %F\n", g.zLogin);
1520 md5sum_blob(&ctrl, &cksum);
1521 blob_appendf(&ctrl, "Z %b\n", &cksum);
1522 db_begin_transaction();
1523 g.markPrivate = content_is_private(rid);
1524 nrid = content_put(&ctrl, 0, 0);
1525 manifest_crosslink(nrid, &ctrl);
1526 db_end_transaction(0);
1527 }
1528 cgi_redirectf("ci?name=%s", zUuid);
1529 }
1530
--- src/info.c
+++ src/info.c
@@ -1519,11 +1519,11 @@
1519 blob_appendf(&ctrl, "U %F\n", g.zLogin);
1520 md5sum_blob(&ctrl, &cksum);
1521 blob_appendf(&ctrl, "Z %b\n", &cksum);
1522 db_begin_transaction();
1523 g.markPrivate = content_is_private(rid);
1524 nrid = content_put(&ctrl, 0, 0, 0);
1525 manifest_crosslink(nrid, &ctrl);
1526 db_end_transaction(0);
1527 }
1528 cgi_redirectf("ci?name=%s", zUuid);
1529 }
1530
+1 -1
--- src/rebuild.c
+++ src/rebuild.c
@@ -518,11 +518,11 @@
518518
blob_appendf(&path, "%s", zSubpath);
519519
if( blob_read_from_file(&aContent, blob_str(&path))==-1 ){
520520
fossil_panic("some unknown error occurred while reading \"%s\"",
521521
blob_str(&path));
522522
}
523
- content_put(&aContent, 0, 0);
523
+ content_put(&aContent, 0, 0, 0);
524524
blob_reset(&path);
525525
blob_reset(&aContent);
526526
free(zSubpath);
527527
printf("\r%d", ++nFileRead);
528528
fflush(stdout);
529529
--- src/rebuild.c
+++ src/rebuild.c
@@ -518,11 +518,11 @@
518 blob_appendf(&path, "%s", zSubpath);
519 if( blob_read_from_file(&aContent, blob_str(&path))==-1 ){
520 fossil_panic("some unknown error occurred while reading \"%s\"",
521 blob_str(&path));
522 }
523 content_put(&aContent, 0, 0);
524 blob_reset(&path);
525 blob_reset(&aContent);
526 free(zSubpath);
527 printf("\r%d", ++nFileRead);
528 fflush(stdout);
529
--- src/rebuild.c
+++ src/rebuild.c
@@ -518,11 +518,11 @@
518 blob_appendf(&path, "%s", zSubpath);
519 if( blob_read_from_file(&aContent, blob_str(&path))==-1 ){
520 fossil_panic("some unknown error occurred while reading \"%s\"",
521 blob_str(&path));
522 }
523 content_put(&aContent, 0, 0, 0);
524 blob_reset(&path);
525 blob_reset(&aContent);
526 free(zSubpath);
527 printf("\r%d", ++nFileRead);
528 fflush(stdout);
529
+1 -1
--- src/tag.c
+++ src/tag.c
@@ -307,11 +307,11 @@
307307
blob_appendf(&ctrl, "\n");
308308
}
309309
blob_appendf(&ctrl, "U %F\n", zUserOvrd ? zUserOvrd : g.zLogin);
310310
md5sum_blob(&ctrl, &cksum);
311311
blob_appendf(&ctrl, "Z %b\n", &cksum);
312
- nrid = content_put(&ctrl, 0, 0);
312
+ nrid = content_put(&ctrl, 0, 0, 0);
313313
manifest_crosslink(nrid, &ctrl);
314314
}
315315
316316
/*
317317
** COMMAND: tag
318318
--- src/tag.c
+++ src/tag.c
@@ -307,11 +307,11 @@
307 blob_appendf(&ctrl, "\n");
308 }
309 blob_appendf(&ctrl, "U %F\n", zUserOvrd ? zUserOvrd : g.zLogin);
310 md5sum_blob(&ctrl, &cksum);
311 blob_appendf(&ctrl, "Z %b\n", &cksum);
312 nrid = content_put(&ctrl, 0, 0);
313 manifest_crosslink(nrid, &ctrl);
314 }
315
316 /*
317 ** COMMAND: tag
318
--- src/tag.c
+++ src/tag.c
@@ -307,11 +307,11 @@
307 blob_appendf(&ctrl, "\n");
308 }
309 blob_appendf(&ctrl, "U %F\n", zUserOvrd ? zUserOvrd : g.zLogin);
310 md5sum_blob(&ctrl, &cksum);
311 blob_appendf(&ctrl, "Z %b\n", &cksum);
312 nrid = content_put(&ctrl, 0, 0, 0);
313 manifest_crosslink(nrid, &ctrl);
314 }
315
316 /*
317 ** COMMAND: tag
318
+2 -2
--- src/tkt.c
+++ src/tkt.c
@@ -480,11 +480,11 @@
480480
}else if( g.thTrace ){
481481
Th_Trace("submit_ticket {\n<blockquote><pre>\n%h\n</pre></blockquote>\n"
482482
"}<br />\n",
483483
blob_str(&tktchng));
484484
}else{
485
- rid = content_put(&tktchng, 0, 0);
485
+ rid = content_put(&tktchng, 0, 0, 0);
486486
if( rid==0 ){
487487
fossil_panic("trouble committing ticket: %s", g.zErrMsg);
488488
}
489489
manifest_crosslink_begin();
490490
manifest_crosslink(rid, &tktchng);
@@ -1056,11 +1056,11 @@
10561056
}
10571057
blob_appendf(&tktchng, "K %s\n", zTktUuid);
10581058
blob_appendf(&tktchng, "U %F\n", g.zLogin);
10591059
md5sum_blob(&tktchng, &cksum);
10601060
blob_appendf(&tktchng, "Z %b\n", &cksum);
1061
- rid = content_put(&tktchng, 0, 0);
1061
+ rid = content_put(&tktchng, 0, 0, 0);
10621062
if( rid==0 ){
10631063
fossil_panic("trouble committing ticket: %s", g.zErrMsg);
10641064
}
10651065
manifest_crosslink_begin();
10661066
manifest_crosslink(rid, &tktchng);
10671067
--- src/tkt.c
+++ src/tkt.c
@@ -480,11 +480,11 @@
480 }else if( g.thTrace ){
481 Th_Trace("submit_ticket {\n<blockquote><pre>\n%h\n</pre></blockquote>\n"
482 "}<br />\n",
483 blob_str(&tktchng));
484 }else{
485 rid = content_put(&tktchng, 0, 0);
486 if( rid==0 ){
487 fossil_panic("trouble committing ticket: %s", g.zErrMsg);
488 }
489 manifest_crosslink_begin();
490 manifest_crosslink(rid, &tktchng);
@@ -1056,11 +1056,11 @@
1056 }
1057 blob_appendf(&tktchng, "K %s\n", zTktUuid);
1058 blob_appendf(&tktchng, "U %F\n", g.zLogin);
1059 md5sum_blob(&tktchng, &cksum);
1060 blob_appendf(&tktchng, "Z %b\n", &cksum);
1061 rid = content_put(&tktchng, 0, 0);
1062 if( rid==0 ){
1063 fossil_panic("trouble committing ticket: %s", g.zErrMsg);
1064 }
1065 manifest_crosslink_begin();
1066 manifest_crosslink(rid, &tktchng);
1067
--- src/tkt.c
+++ src/tkt.c
@@ -480,11 +480,11 @@
480 }else if( g.thTrace ){
481 Th_Trace("submit_ticket {\n<blockquote><pre>\n%h\n</pre></blockquote>\n"
482 "}<br />\n",
483 blob_str(&tktchng));
484 }else{
485 rid = content_put(&tktchng, 0, 0, 0);
486 if( rid==0 ){
487 fossil_panic("trouble committing ticket: %s", g.zErrMsg);
488 }
489 manifest_crosslink_begin();
490 manifest_crosslink(rid, &tktchng);
@@ -1056,11 +1056,11 @@
1056 }
1057 blob_appendf(&tktchng, "K %s\n", zTktUuid);
1058 blob_appendf(&tktchng, "U %F\n", g.zLogin);
1059 md5sum_blob(&tktchng, &cksum);
1060 blob_appendf(&tktchng, "Z %b\n", &cksum);
1061 rid = content_put(&tktchng, 0, 0, 0);
1062 if( rid==0 ){
1063 fossil_panic("trouble committing ticket: %s", g.zErrMsg);
1064 }
1065 manifest_crosslink_begin();
1066 manifest_crosslink(rid, &tktchng);
1067
+3 -3
--- src/wiki.c
+++ src/wiki.c
@@ -322,11 +322,11 @@
322322
}
323323
blob_appendf(&wiki, "W %d\n%s\n", strlen(zBody), zBody);
324324
md5sum_blob(&wiki, &cksum);
325325
blob_appendf(&wiki, "Z %b\n", &cksum);
326326
blob_reset(&cksum);
327
- nrid = content_put(&wiki, 0, 0);
327
+ nrid = content_put(&wiki, 0, 0, 0);
328328
db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
329329
manifest_crosslink(nrid, &wiki);
330330
blob_reset(&wiki);
331331
content_deltify(rid, nrid, 0);
332332
}
@@ -495,11 +495,11 @@
495495
appendRemark(&body);
496496
blob_appendf(&wiki, "W %d\n%s\n", blob_size(&body), blob_str(&body));
497497
md5sum_blob(&wiki, &cksum);
498498
blob_appendf(&wiki, "Z %b\n", &cksum);
499499
blob_reset(&cksum);
500
- nrid = content_put(&wiki, 0, 0);
500
+ nrid = content_put(&wiki, 0, 0, 0);
501501
db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
502502
manifest_crosslink(nrid, &wiki);
503503
blob_reset(&wiki);
504504
content_deltify(rid, nrid, 0);
505505
db_end_transaction(0);
@@ -820,11 +820,11 @@
820820
blob_str(pContent) );
821821
md5sum_blob(&wiki, &cksum);
822822
blob_appendf(&wiki, "Z %b\n", &cksum);
823823
blob_reset(&cksum);
824824
db_begin_transaction();
825
- nrid = content_put( &wiki, 0, 0 );
825
+ nrid = content_put( &wiki, 0, 0, 0);
826826
db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
827827
manifest_crosslink(nrid,&wiki);
828828
blob_reset(&wiki);
829829
content_deltify(rid,nrid,0);
830830
db_end_transaction(0);
831831
--- src/wiki.c
+++ src/wiki.c
@@ -322,11 +322,11 @@
322 }
323 blob_appendf(&wiki, "W %d\n%s\n", strlen(zBody), zBody);
324 md5sum_blob(&wiki, &cksum);
325 blob_appendf(&wiki, "Z %b\n", &cksum);
326 blob_reset(&cksum);
327 nrid = content_put(&wiki, 0, 0);
328 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
329 manifest_crosslink(nrid, &wiki);
330 blob_reset(&wiki);
331 content_deltify(rid, nrid, 0);
332 }
@@ -495,11 +495,11 @@
495 appendRemark(&body);
496 blob_appendf(&wiki, "W %d\n%s\n", blob_size(&body), blob_str(&body));
497 md5sum_blob(&wiki, &cksum);
498 blob_appendf(&wiki, "Z %b\n", &cksum);
499 blob_reset(&cksum);
500 nrid = content_put(&wiki, 0, 0);
501 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
502 manifest_crosslink(nrid, &wiki);
503 blob_reset(&wiki);
504 content_deltify(rid, nrid, 0);
505 db_end_transaction(0);
@@ -820,11 +820,11 @@
820 blob_str(pContent) );
821 md5sum_blob(&wiki, &cksum);
822 blob_appendf(&wiki, "Z %b\n", &cksum);
823 blob_reset(&cksum);
824 db_begin_transaction();
825 nrid = content_put( &wiki, 0, 0 );
826 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
827 manifest_crosslink(nrid,&wiki);
828 blob_reset(&wiki);
829 content_deltify(rid,nrid,0);
830 db_end_transaction(0);
831
--- src/wiki.c
+++ src/wiki.c
@@ -322,11 +322,11 @@
322 }
323 blob_appendf(&wiki, "W %d\n%s\n", strlen(zBody), zBody);
324 md5sum_blob(&wiki, &cksum);
325 blob_appendf(&wiki, "Z %b\n", &cksum);
326 blob_reset(&cksum);
327 nrid = content_put(&wiki, 0, 0, 0);
328 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
329 manifest_crosslink(nrid, &wiki);
330 blob_reset(&wiki);
331 content_deltify(rid, nrid, 0);
332 }
@@ -495,11 +495,11 @@
495 appendRemark(&body);
496 blob_appendf(&wiki, "W %d\n%s\n", blob_size(&body), blob_str(&body));
497 md5sum_blob(&wiki, &cksum);
498 blob_appendf(&wiki, "Z %b\n", &cksum);
499 blob_reset(&cksum);
500 nrid = content_put(&wiki, 0, 0, 0);
501 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
502 manifest_crosslink(nrid, &wiki);
503 blob_reset(&wiki);
504 content_deltify(rid, nrid, 0);
505 db_end_transaction(0);
@@ -820,11 +820,11 @@
820 blob_str(pContent) );
821 md5sum_blob(&wiki, &cksum);
822 blob_appendf(&wiki, "Z %b\n", &cksum);
823 blob_reset(&cksum);
824 db_begin_transaction();
825 nrid = content_put( &wiki, 0, 0, 0);
826 db_multi_exec("INSERT OR IGNORE INTO unsent VALUES(%d)", nrid);
827 manifest_crosslink(nrid,&wiki);
828 blob_reset(&wiki);
829 content_deltify(rid,nrid,0);
830 db_end_transaction(0);
831
+152 -11
--- src/xfer.c
+++ src/xfer.c
@@ -27,11 +27,11 @@
2727
typedef struct Xfer Xfer;
2828
struct Xfer {
2929
Blob *pIn; /* Input text from the other side */
3030
Blob *pOut; /* Compose our reply here */
3131
Blob line; /* The current line of input */
32
- Blob aToken[5]; /* Tokenized version of line */
32
+ Blob aToken[6]; /* Tokenized version of line */
3333
Blob err; /* Error message text */
3434
int nToken; /* Number of tokens in line */
3535
int nIGotSent; /* Number of "igot" cards sent */
3636
int nGimmeSent; /* Number of gimme cards sent */
3737
int nFileSent; /* Number of files sent */
@@ -132,20 +132,20 @@
132132
pXfer->nDeltaRcvd++;
133133
}else{
134134
srcid = 0;
135135
pXfer->nFileRcvd++;
136136
}
137
- rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid);
137
+ rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid, 0);
138138
remote_has(rid);
139139
blob_reset(&content);
140140
return;
141141
}
142142
if( pXfer->nToken==4 ){
143143
Blob src, next;
144144
srcid = rid_from_uuid(&pXfer->aToken[2], 1);
145145
if( content_get(srcid, &src)==0 ){
146
- rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid);
146
+ rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid, 0);
147147
pXfer->nDanglingFile++;
148148
db_multi_exec("DELETE FROM phantom WHERE rid=%d", rid);
149149
content_make_public(rid);
150150
return;
151151
}
@@ -159,20 +159,79 @@
159159
}
160160
sha1sum_blob(&content, &hash);
161161
if( !blob_eq_str(&pXfer->aToken[1], blob_str(&hash), -1) ){
162162
blob_appendf(&pXfer->err, "content does not match sha1 hash");
163163
}
164
- rid = content_put(&content, blob_str(&hash), 0);
164
+ rid = content_put(&content, blob_str(&hash), 0, 0);
165165
blob_reset(&hash);
166166
if( rid==0 ){
167167
blob_appendf(&pXfer->err, "%s", g.zErrMsg);
168168
}else{
169169
content_make_public(rid);
170170
manifest_crosslink(rid, &content);
171171
}
172172
remote_has(rid);
173173
}
174
+
175
+/*
176
+** The aToken[0..nToken-1] blob array is a parse of a "cfile" line
177
+** message. This routine finishes parsing that message and does
178
+** a record insert of the file. The difference between "file" and
179
+** "cfile" is that with "cfile" the content is already compressed.
180
+**
181
+** The file line is in one of the following two forms:
182
+**
183
+** cfile UUID USIZE CSIZE \n CONTENT
184
+** cfile UUID DELTASRC USIZE CSIZE \n CONTENT
185
+**
186
+** The content is CSIZE bytes immediately following the newline.
187
+** If DELTASRC exists, then the CONTENT is a delta against the
188
+** content of DELTASRC.
189
+**
190
+** The original size of the UUID artifact is USIZE.
191
+**
192
+** If any error occurs, write a message into pErr which has already
193
+** be initialized to an empty string.
194
+**
195
+** Any artifact successfully received by this routine is considered to
196
+** be public and is therefore removed from the "private" table.
197
+*/
198
+static void xfer_accept_compressed_file(Xfer *pXfer){
199
+ int szC; /* CSIZE */
200
+ int szU; /* USIZE */
201
+ int rid;
202
+ int srcid = 0;
203
+ Blob content;
204
+
205
+ if( pXfer->nToken<4
206
+ || pXfer->nToken>5
207
+ || !blob_is_uuid(&pXfer->aToken[1])
208
+ || !blob_is_int(&pXfer->aToken[pXfer->nToken-2], &szU)
209
+ || !blob_is_int(&pXfer->aToken[pXfer->nToken-1], &szC)
210
+ || szC<0 || szU<0
211
+ || (pXfer->nToken==5 && !blob_is_uuid(&pXfer->aToken[2]))
212
+ ){
213
+ blob_appendf(&pXfer->err, "malformed cfile line");
214
+ return;
215
+ }
216
+ blob_zero(&content);
217
+ blob_extract(pXfer->pIn, szC, &content);
218
+ if( uuid_is_shunned(blob_str(&pXfer->aToken[1])) ){
219
+ /* Ignore files that have been shunned */
220
+ return;
221
+ }
222
+ if( pXfer->nToken==5 ){
223
+ srcid = rid_from_uuid(&pXfer->aToken[2], 1);
224
+ pXfer->nDeltaRcvd++;
225
+ }else{
226
+ srcid = 0;
227
+ pXfer->nFileRcvd++;
228
+ }
229
+ rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid, szC);
230
+ remote_has(rid);
231
+ blob_reset(&content);
232
+}
174233
175234
/*
176235
** Try to send a file as a delta against its parent.
177236
** If successful, return the number of bytes in the delta.
178237
** If we cannot generate an appropriate delta, then send
@@ -333,10 +392,55 @@
333392
}
334393
}
335394
remote_has(rid);
336395
blob_reset(&uuid);
337396
}
397
+
398
+/*
399
+** Send the file identified by rid as a compressed artifact. Basically,
400
+** send the content exactly as it appears in the BLOB table using
401
+** a "cfile" card.
402
+*/
403
+static void send_compressed_file(Xfer *pXfer, int rid){
404
+ const char *zContent;
405
+ const char *zUuid;
406
+ char *zDelta;
407
+ int szU;
408
+ int szC;
409
+ int rc;
410
+ Stmt s;
411
+
412
+ db_prepare(&s,
413
+ "SELECT uuid, size, content FROM blob"
414
+ " WHERE rid=%d"
415
+ " AND size>=0"
416
+ " AND uuid NOT IN shun"
417
+ " AND rid NOT IN private",
418
+ rid
419
+ );
420
+ rc = db_step(&s);
421
+ if( rc==SQLITE_ROW ){
422
+ zUuid = db_column_text(&s, 0);
423
+ szU = db_column_int(&s, 1);
424
+ szC = db_column_bytes(&s, 2);
425
+ zContent = db_column_raw(&s, 2);
426
+ zDelta = db_text(0, "SELECT uuid FROM blob WHERE rid="
427
+ " (SELECT srcid FROM delta WHERE rid=%d)", rid);
428
+ blob_appendf(pXfer->pOut, "cfile %s ", zUuid);
429
+ if( zDelta ){
430
+ blob_appendf(pXfer->pOut, "%s ", zDelta);
431
+ fossil_free(zDelta);
432
+ pXfer->nDeltaSent++;
433
+ }else{
434
+ pXfer->nFileSent++;
435
+ }
436
+ blob_appendf(pXfer->pOut, "%d %d\n", szU, szC);
437
+ blob_append(pXfer->pOut, zContent, szC);
438
+ blob_append(pXfer->pOut, "\n", 1);
439
+ }
440
+ db_finalize(&s);
441
+}
338442
339443
/*
340444
** Send a gimme message for every phantom.
341445
**
342446
** It should not be possible to have a private phantom. But just to be
@@ -511,11 +615,11 @@
511615
nRow++;
512616
if( nRow>=800 && nUncl>nRow+100 ){
513617
md5sum_blob(&cluster, &cksum);
514618
blob_appendf(&cluster, "Z %b\n", &cksum);
515619
blob_reset(&cksum);
516
- content_put(&cluster, 0, 0);
620
+ content_put(&cluster, 0, 0, 0);
517621
blob_reset(&cluster);
518622
nUncl -= nRow;
519623
nRow = 0;
520624
}
521625
}
@@ -523,11 +627,11 @@
523627
db_multi_exec("DELETE FROM unclustered");
524628
if( nRow>0 ){
525629
md5sum_blob(&cluster, &cksum);
526630
blob_appendf(&cluster, "Z %b\n", &cksum);
527631
blob_reset(&cksum);
528
- content_put(&cluster, 0, 0);
632
+ content_put(&cluster, 0, 0, 0);
529633
blob_reset(&cluster);
530634
}
531635
}
532636
}
533637
@@ -666,10 +770,31 @@
666770
@ error %T(blob_str(&xfer.err))
667771
nErr++;
668772
break;
669773
}
670774
}else
775
+
776
+ /* cfile UUID USIZE CSIZE \n CONTENT
777
+ ** cfile UUID DELTASRC USIZE CSIZE \n CONTENT
778
+ **
779
+ ** Accept a file from the client.
780
+ */
781
+ if( blob_eq(&xfer.aToken[0], "cfile") ){
782
+ if( !isPush ){
783
+ cgi_reset_content();
784
+ @ error not\sauthorized\sto\swrite
785
+ nErr++;
786
+ break;
787
+ }
788
+ xfer_accept_compressed_file(&xfer);
789
+ if( blob_size(&xfer.err) ){
790
+ cgi_reset_content();
791
+ @ error %T(blob_str(&xfer.err))
792
+ nErr++;
793
+ break;
794
+ }
795
+ }else
671796
672797
/* gimme UUID
673798
**
674799
** Client is requesting a file. Send it.
675800
*/
@@ -763,14 +888,21 @@
763888
if( xfer.nToken==3
764889
&& blob_is_int(&xfer.aToken[1], &iVers)
765890
&& iVers>=2
766891
){
767892
int seqno, max;
893
+ if( iVers>=3 ){
894
+ cgi_set_content_type("application/x-fossil-uncompressed");
895
+ }
768896
blob_is_int(&xfer.aToken[2], &seqno);
769897
max = db_int(0, "SELECT max(rid) FROM blob");
770898
while( xfer.mxSend>blob_size(xfer.pOut) && seqno<=max ){
771
- send_file(&xfer, seqno, 0, 1);
899
+ if( iVers>=3 ){
900
+ send_compressed_file(&xfer, seqno);
901
+ }else{
902
+ send_file(&xfer, seqno, 0, 1);
903
+ }
772904
seqno++;
773905
}
774906
if( seqno>=max ) seqno = 0;
775907
@ clone_seqno %d(seqno)
776908
}else{
@@ -1032,11 +1164,11 @@
10321164
10331165
/*
10341166
** Always begin with a clone, pull, or push message
10351167
*/
10361168
if( cloneFlag ){
1037
- blob_appendf(&send, "clone 2 %d\n", cloneSeqno);
1169
+ blob_appendf(&send, "clone 3 %d\n", cloneSeqno);
10381170
pushFlag = 0;
10391171
pullFlag = 0;
10401172
nCardSent++;
10411173
/* TBD: Request all transferable configuration values */
10421174
content_enable_dephantomize(0);
@@ -1191,10 +1323,19 @@
11911323
** Receive a file transmitted from the server.
11921324
*/
11931325
if( blob_eq(&xfer.aToken[0],"file") ){
11941326
xfer_accept_file(&xfer, cloneFlag);
11951327
}else
1328
+
1329
+ /* cfile UUID USIZE CSIZE \n CONTENT
1330
+ ** cfile UUID DELTASRC USIZE CSIZE \n CONTENT
1331
+ **
1332
+ ** Receive a compressed file transmitted from the server.
1333
+ */
1334
+ if( blob_eq(&xfer.aToken[0],"cfile") ){
1335
+ xfer_accept_compressed_file(&xfer);
1336
+ }else
11961337
11971338
/* gimme UUID
11981339
**
11991340
** Server is requesting a file. If the file is a manifest, assume
12001341
** that the server will also want to know all of the content files
@@ -1249,11 +1390,11 @@
12491390
}
12501391
if( zPCode==0 ){
12511392
zPCode = mprintf("%b", &xfer.aToken[2]);
12521393
db_set("project-code", zPCode, 0);
12531394
}
1254
- blob_appendf(&send, "clone 2 %d\n", cloneSeqno);
1395
+ blob_appendf(&send, "clone 3 %d\n", cloneSeqno);
12551396
nCardSent++;
12561397
}else
12571398
12581399
/* config NAME SIZE \n CONTENT
12591400
**
@@ -1363,20 +1504,20 @@
13631504
break;
13641505
}
13651506
}else
13661507
13671508
/* Unknown message */
1368
- {
1509
+ if( xfer.nToken>0 ){
13691510
if( blob_str(&xfer.aToken[0])[0]=='<' ){
13701511
fossil_warning(
13711512
"server replies with HTML instead of fossil sync protocol:\n%b",
13721513
&recv
13731514
);
13741515
nErr++;
13751516
break;
13761517
}
1377
- blob_appendf(&xfer.err, "unknown command: %b", &xfer.aToken[0]);
1518
+ blob_appendf(&xfer.err, "unknown command: [%b]", &xfer.aToken[0]);
13781519
}
13791520
13801521
if( blob_size(&xfer.err) ){
13811522
fossil_warning("%b", &xfer.err);
13821523
nErr++;
13831524
--- src/xfer.c
+++ src/xfer.c
@@ -27,11 +27,11 @@
27 typedef struct Xfer Xfer;
28 struct Xfer {
29 Blob *pIn; /* Input text from the other side */
30 Blob *pOut; /* Compose our reply here */
31 Blob line; /* The current line of input */
32 Blob aToken[5]; /* Tokenized version of line */
33 Blob err; /* Error message text */
34 int nToken; /* Number of tokens in line */
35 int nIGotSent; /* Number of "igot" cards sent */
36 int nGimmeSent; /* Number of gimme cards sent */
37 int nFileSent; /* Number of files sent */
@@ -132,20 +132,20 @@
132 pXfer->nDeltaRcvd++;
133 }else{
134 srcid = 0;
135 pXfer->nFileRcvd++;
136 }
137 rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid);
138 remote_has(rid);
139 blob_reset(&content);
140 return;
141 }
142 if( pXfer->nToken==4 ){
143 Blob src, next;
144 srcid = rid_from_uuid(&pXfer->aToken[2], 1);
145 if( content_get(srcid, &src)==0 ){
146 rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid);
147 pXfer->nDanglingFile++;
148 db_multi_exec("DELETE FROM phantom WHERE rid=%d", rid);
149 content_make_public(rid);
150 return;
151 }
@@ -159,20 +159,79 @@
159 }
160 sha1sum_blob(&content, &hash);
161 if( !blob_eq_str(&pXfer->aToken[1], blob_str(&hash), -1) ){
162 blob_appendf(&pXfer->err, "content does not match sha1 hash");
163 }
164 rid = content_put(&content, blob_str(&hash), 0);
165 blob_reset(&hash);
166 if( rid==0 ){
167 blob_appendf(&pXfer->err, "%s", g.zErrMsg);
168 }else{
169 content_make_public(rid);
170 manifest_crosslink(rid, &content);
171 }
172 remote_has(rid);
173 }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
174
175 /*
176 ** Try to send a file as a delta against its parent.
177 ** If successful, return the number of bytes in the delta.
178 ** If we cannot generate an appropriate delta, then send
@@ -333,10 +392,55 @@
333 }
334 }
335 remote_has(rid);
336 blob_reset(&uuid);
337 }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
338
339 /*
340 ** Send a gimme message for every phantom.
341 **
342 ** It should not be possible to have a private phantom. But just to be
@@ -511,11 +615,11 @@
511 nRow++;
512 if( nRow>=800 && nUncl>nRow+100 ){
513 md5sum_blob(&cluster, &cksum);
514 blob_appendf(&cluster, "Z %b\n", &cksum);
515 blob_reset(&cksum);
516 content_put(&cluster, 0, 0);
517 blob_reset(&cluster);
518 nUncl -= nRow;
519 nRow = 0;
520 }
521 }
@@ -523,11 +627,11 @@
523 db_multi_exec("DELETE FROM unclustered");
524 if( nRow>0 ){
525 md5sum_blob(&cluster, &cksum);
526 blob_appendf(&cluster, "Z %b\n", &cksum);
527 blob_reset(&cksum);
528 content_put(&cluster, 0, 0);
529 blob_reset(&cluster);
530 }
531 }
532 }
533
@@ -666,10 +770,31 @@
666 @ error %T(blob_str(&xfer.err))
667 nErr++;
668 break;
669 }
670 }else
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
671
672 /* gimme UUID
673 **
674 ** Client is requesting a file. Send it.
675 */
@@ -763,14 +888,21 @@
763 if( xfer.nToken==3
764 && blob_is_int(&xfer.aToken[1], &iVers)
765 && iVers>=2
766 ){
767 int seqno, max;
 
 
 
768 blob_is_int(&xfer.aToken[2], &seqno);
769 max = db_int(0, "SELECT max(rid) FROM blob");
770 while( xfer.mxSend>blob_size(xfer.pOut) && seqno<=max ){
771 send_file(&xfer, seqno, 0, 1);
 
 
 
 
772 seqno++;
773 }
774 if( seqno>=max ) seqno = 0;
775 @ clone_seqno %d(seqno)
776 }else{
@@ -1032,11 +1164,11 @@
1032
1033 /*
1034 ** Always begin with a clone, pull, or push message
1035 */
1036 if( cloneFlag ){
1037 blob_appendf(&send, "clone 2 %d\n", cloneSeqno);
1038 pushFlag = 0;
1039 pullFlag = 0;
1040 nCardSent++;
1041 /* TBD: Request all transferable configuration values */
1042 content_enable_dephantomize(0);
@@ -1191,10 +1323,19 @@
1191 ** Receive a file transmitted from the server.
1192 */
1193 if( blob_eq(&xfer.aToken[0],"file") ){
1194 xfer_accept_file(&xfer, cloneFlag);
1195 }else
 
 
 
 
 
 
 
 
 
1196
1197 /* gimme UUID
1198 **
1199 ** Server is requesting a file. If the file is a manifest, assume
1200 ** that the server will also want to know all of the content files
@@ -1249,11 +1390,11 @@
1249 }
1250 if( zPCode==0 ){
1251 zPCode = mprintf("%b", &xfer.aToken[2]);
1252 db_set("project-code", zPCode, 0);
1253 }
1254 blob_appendf(&send, "clone 2 %d\n", cloneSeqno);
1255 nCardSent++;
1256 }else
1257
1258 /* config NAME SIZE \n CONTENT
1259 **
@@ -1363,20 +1504,20 @@
1363 break;
1364 }
1365 }else
1366
1367 /* Unknown message */
1368 {
1369 if( blob_str(&xfer.aToken[0])[0]=='<' ){
1370 fossil_warning(
1371 "server replies with HTML instead of fossil sync protocol:\n%b",
1372 &recv
1373 );
1374 nErr++;
1375 break;
1376 }
1377 blob_appendf(&xfer.err, "unknown command: %b", &xfer.aToken[0]);
1378 }
1379
1380 if( blob_size(&xfer.err) ){
1381 fossil_warning("%b", &xfer.err);
1382 nErr++;
1383
--- src/xfer.c
+++ src/xfer.c
@@ -27,11 +27,11 @@
27 typedef struct Xfer Xfer;
28 struct Xfer {
29 Blob *pIn; /* Input text from the other side */
30 Blob *pOut; /* Compose our reply here */
31 Blob line; /* The current line of input */
32 Blob aToken[6]; /* Tokenized version of line */
33 Blob err; /* Error message text */
34 int nToken; /* Number of tokens in line */
35 int nIGotSent; /* Number of "igot" cards sent */
36 int nGimmeSent; /* Number of gimme cards sent */
37 int nFileSent; /* Number of files sent */
@@ -132,20 +132,20 @@
132 pXfer->nDeltaRcvd++;
133 }else{
134 srcid = 0;
135 pXfer->nFileRcvd++;
136 }
137 rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid, 0);
138 remote_has(rid);
139 blob_reset(&content);
140 return;
141 }
142 if( pXfer->nToken==4 ){
143 Blob src, next;
144 srcid = rid_from_uuid(&pXfer->aToken[2], 1);
145 if( content_get(srcid, &src)==0 ){
146 rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid, 0);
147 pXfer->nDanglingFile++;
148 db_multi_exec("DELETE FROM phantom WHERE rid=%d", rid);
149 content_make_public(rid);
150 return;
151 }
@@ -159,20 +159,79 @@
159 }
160 sha1sum_blob(&content, &hash);
161 if( !blob_eq_str(&pXfer->aToken[1], blob_str(&hash), -1) ){
162 blob_appendf(&pXfer->err, "content does not match sha1 hash");
163 }
164 rid = content_put(&content, blob_str(&hash), 0, 0);
165 blob_reset(&hash);
166 if( rid==0 ){
167 blob_appendf(&pXfer->err, "%s", g.zErrMsg);
168 }else{
169 content_make_public(rid);
170 manifest_crosslink(rid, &content);
171 }
172 remote_has(rid);
173 }
174
175 /*
176 ** The aToken[0..nToken-1] blob array is a parse of a "cfile" line
177 ** message. This routine finishes parsing that message and does
178 ** a record insert of the file. The difference between "file" and
179 ** "cfile" is that with "cfile" the content is already compressed.
180 **
181 ** The file line is in one of the following two forms:
182 **
183 ** cfile UUID USIZE CSIZE \n CONTENT
184 ** cfile UUID DELTASRC USIZE CSIZE \n CONTENT
185 **
186 ** The content is CSIZE bytes immediately following the newline.
187 ** If DELTASRC exists, then the CONTENT is a delta against the
188 ** content of DELTASRC.
189 **
190 ** The original size of the UUID artifact is USIZE.
191 **
192 ** If any error occurs, write a message into pErr which has already
193 ** be initialized to an empty string.
194 **
195 ** Any artifact successfully received by this routine is considered to
196 ** be public and is therefore removed from the "private" table.
197 */
198 static void xfer_accept_compressed_file(Xfer *pXfer){
199 int szC; /* CSIZE */
200 int szU; /* USIZE */
201 int rid;
202 int srcid = 0;
203 Blob content;
204
205 if( pXfer->nToken<4
206 || pXfer->nToken>5
207 || !blob_is_uuid(&pXfer->aToken[1])
208 || !blob_is_int(&pXfer->aToken[pXfer->nToken-2], &szU)
209 || !blob_is_int(&pXfer->aToken[pXfer->nToken-1], &szC)
210 || szC<0 || szU<0
211 || (pXfer->nToken==5 && !blob_is_uuid(&pXfer->aToken[2]))
212 ){
213 blob_appendf(&pXfer->err, "malformed cfile line");
214 return;
215 }
216 blob_zero(&content);
217 blob_extract(pXfer->pIn, szC, &content);
218 if( uuid_is_shunned(blob_str(&pXfer->aToken[1])) ){
219 /* Ignore files that have been shunned */
220 return;
221 }
222 if( pXfer->nToken==5 ){
223 srcid = rid_from_uuid(&pXfer->aToken[2], 1);
224 pXfer->nDeltaRcvd++;
225 }else{
226 srcid = 0;
227 pXfer->nFileRcvd++;
228 }
229 rid = content_put(&content, blob_str(&pXfer->aToken[1]), srcid, szC);
230 remote_has(rid);
231 blob_reset(&content);
232 }
233
234 /*
235 ** Try to send a file as a delta against its parent.
236 ** If successful, return the number of bytes in the delta.
237 ** If we cannot generate an appropriate delta, then send
@@ -333,10 +392,55 @@
392 }
393 }
394 remote_has(rid);
395 blob_reset(&uuid);
396 }
397
398 /*
399 ** Send the file identified by rid as a compressed artifact. Basically,
400 ** send the content exactly as it appears in the BLOB table using
401 ** a "cfile" card.
402 */
403 static void send_compressed_file(Xfer *pXfer, int rid){
404 const char *zContent;
405 const char *zUuid;
406 char *zDelta;
407 int szU;
408 int szC;
409 int rc;
410 Stmt s;
411
412 db_prepare(&s,
413 "SELECT uuid, size, content FROM blob"
414 " WHERE rid=%d"
415 " AND size>=0"
416 " AND uuid NOT IN shun"
417 " AND rid NOT IN private",
418 rid
419 );
420 rc = db_step(&s);
421 if( rc==SQLITE_ROW ){
422 zUuid = db_column_text(&s, 0);
423 szU = db_column_int(&s, 1);
424 szC = db_column_bytes(&s, 2);
425 zContent = db_column_raw(&s, 2);
426 zDelta = db_text(0, "SELECT uuid FROM blob WHERE rid="
427 " (SELECT srcid FROM delta WHERE rid=%d)", rid);
428 blob_appendf(pXfer->pOut, "cfile %s ", zUuid);
429 if( zDelta ){
430 blob_appendf(pXfer->pOut, "%s ", zDelta);
431 fossil_free(zDelta);
432 pXfer->nDeltaSent++;
433 }else{
434 pXfer->nFileSent++;
435 }
436 blob_appendf(pXfer->pOut, "%d %d\n", szU, szC);
437 blob_append(pXfer->pOut, zContent, szC);
438 blob_append(pXfer->pOut, "\n", 1);
439 }
440 db_finalize(&s);
441 }
442
443 /*
444 ** Send a gimme message for every phantom.
445 **
446 ** It should not be possible to have a private phantom. But just to be
@@ -511,11 +615,11 @@
615 nRow++;
616 if( nRow>=800 && nUncl>nRow+100 ){
617 md5sum_blob(&cluster, &cksum);
618 blob_appendf(&cluster, "Z %b\n", &cksum);
619 blob_reset(&cksum);
620 content_put(&cluster, 0, 0, 0);
621 blob_reset(&cluster);
622 nUncl -= nRow;
623 nRow = 0;
624 }
625 }
@@ -523,11 +627,11 @@
627 db_multi_exec("DELETE FROM unclustered");
628 if( nRow>0 ){
629 md5sum_blob(&cluster, &cksum);
630 blob_appendf(&cluster, "Z %b\n", &cksum);
631 blob_reset(&cksum);
632 content_put(&cluster, 0, 0, 0);
633 blob_reset(&cluster);
634 }
635 }
636 }
637
@@ -666,10 +770,31 @@
770 @ error %T(blob_str(&xfer.err))
771 nErr++;
772 break;
773 }
774 }else
775
776 /* cfile UUID USIZE CSIZE \n CONTENT
777 ** cfile UUID DELTASRC USIZE CSIZE \n CONTENT
778 **
779 ** Accept a file from the client.
780 */
781 if( blob_eq(&xfer.aToken[0], "cfile") ){
782 if( !isPush ){
783 cgi_reset_content();
784 @ error not\sauthorized\sto\swrite
785 nErr++;
786 break;
787 }
788 xfer_accept_compressed_file(&xfer);
789 if( blob_size(&xfer.err) ){
790 cgi_reset_content();
791 @ error %T(blob_str(&xfer.err))
792 nErr++;
793 break;
794 }
795 }else
796
797 /* gimme UUID
798 **
799 ** Client is requesting a file. Send it.
800 */
@@ -763,14 +888,21 @@
888 if( xfer.nToken==3
889 && blob_is_int(&xfer.aToken[1], &iVers)
890 && iVers>=2
891 ){
892 int seqno, max;
893 if( iVers>=3 ){
894 cgi_set_content_type("application/x-fossil-uncompressed");
895 }
896 blob_is_int(&xfer.aToken[2], &seqno);
897 max = db_int(0, "SELECT max(rid) FROM blob");
898 while( xfer.mxSend>blob_size(xfer.pOut) && seqno<=max ){
899 if( iVers>=3 ){
900 send_compressed_file(&xfer, seqno);
901 }else{
902 send_file(&xfer, seqno, 0, 1);
903 }
904 seqno++;
905 }
906 if( seqno>=max ) seqno = 0;
907 @ clone_seqno %d(seqno)
908 }else{
@@ -1032,11 +1164,11 @@
1164
1165 /*
1166 ** Always begin with a clone, pull, or push message
1167 */
1168 if( cloneFlag ){
1169 blob_appendf(&send, "clone 3 %d\n", cloneSeqno);
1170 pushFlag = 0;
1171 pullFlag = 0;
1172 nCardSent++;
1173 /* TBD: Request all transferable configuration values */
1174 content_enable_dephantomize(0);
@@ -1191,10 +1323,19 @@
1323 ** Receive a file transmitted from the server.
1324 */
1325 if( blob_eq(&xfer.aToken[0],"file") ){
1326 xfer_accept_file(&xfer, cloneFlag);
1327 }else
1328
1329 /* cfile UUID USIZE CSIZE \n CONTENT
1330 ** cfile UUID DELTASRC USIZE CSIZE \n CONTENT
1331 **
1332 ** Receive a compressed file transmitted from the server.
1333 */
1334 if( blob_eq(&xfer.aToken[0],"cfile") ){
1335 xfer_accept_compressed_file(&xfer);
1336 }else
1337
1338 /* gimme UUID
1339 **
1340 ** Server is requesting a file. If the file is a manifest, assume
1341 ** that the server will also want to know all of the content files
@@ -1249,11 +1390,11 @@
1390 }
1391 if( zPCode==0 ){
1392 zPCode = mprintf("%b", &xfer.aToken[2]);
1393 db_set("project-code", zPCode, 0);
1394 }
1395 blob_appendf(&send, "clone 3 %d\n", cloneSeqno);
1396 nCardSent++;
1397 }else
1398
1399 /* config NAME SIZE \n CONTENT
1400 **
@@ -1363,20 +1504,20 @@
1504 break;
1505 }
1506 }else
1507
1508 /* Unknown message */
1509 if( xfer.nToken>0 ){
1510 if( blob_str(&xfer.aToken[0])[0]=='<' ){
1511 fossil_warning(
1512 "server replies with HTML instead of fossil sync protocol:\n%b",
1513 &recv
1514 );
1515 nErr++;
1516 break;
1517 }
1518 blob_appendf(&xfer.err, "unknown command: [%b]", &xfer.aToken[0]);
1519 }
1520
1521 if( blob_size(&xfer.err) ){
1522 fossil_warning("%b", &xfer.err);
1523 nErr++;
1524

Keyboard Shortcuts

Open search /
Next entry (timeline) j
Previous entry (timeline) k
Open focused entry Enter
Show this help ?
Toggle theme Top nav button