Fossil SCM

Progress on getting private sync to work. Cloning with --private works. Sync also works, but it currently loses the private marker.

drh 2011-02-27 03:12 UTC private-sync
Commit 6da5d4ad5f478c99e81b3a11f5c411d60abdb239
3 files changed +1 -1 -1 +38 -24
+1 -1
--- src/login.c
+++ src/login.c
@@ -374,11 +374,11 @@
374374
&& db_get_int("localauth",0)==0
375375
&& P("HTTPS")==0
376376
){
377377
uid = db_int(0, "SELECT uid FROM user WHERE cap LIKE '%%s%%'");
378378
g.zLogin = db_text("?", "SELECT login FROM user WHERE uid=%d", uid);
379
- zCap = "s";
379
+ zCap = "sx";
380380
g.noPswd = 1;
381381
sqlite3_snprintf(sizeof(g.zCsrfToken), g.zCsrfToken, "localhost");
382382
}
383383
384384
/* Check the login cookie to see if it matches a known valid user.
385385
--- src/login.c
+++ src/login.c
@@ -374,11 +374,11 @@
374 && db_get_int("localauth",0)==0
375 && P("HTTPS")==0
376 ){
377 uid = db_int(0, "SELECT uid FROM user WHERE cap LIKE '%%s%%'");
378 g.zLogin = db_text("?", "SELECT login FROM user WHERE uid=%d", uid);
379 zCap = "s";
380 g.noPswd = 1;
381 sqlite3_snprintf(sizeof(g.zCsrfToken), g.zCsrfToken, "localhost");
382 }
383
384 /* Check the login cookie to see if it matches a known valid user.
385
--- src/login.c
+++ src/login.c
@@ -374,11 +374,11 @@
374 && db_get_int("localauth",0)==0
375 && P("HTTPS")==0
376 ){
377 uid = db_int(0, "SELECT uid FROM user WHERE cap LIKE '%%s%%'");
378 g.zLogin = db_text("?", "SELECT login FROM user WHERE uid=%d", uid);
379 zCap = "sx";
380 g.noPswd = 1;
381 sqlite3_snprintf(sizeof(g.zCsrfToken), g.zCsrfToken, "localhost");
382 }
383
384 /* Check the login cookie to see if it matches a known valid user.
385
--- src/setup.c
+++ src/setup.c
@@ -122,11 +122,10 @@
122122
@ <th class="usetupListCon" style="text-align: left;">Contact&nbsp;Info</th>
123123
@ </tr>
124124
db_prepare(&s, "SELECT uid, login, cap, info FROM user ORDER BY login");
125125
while( db_step(&s)==SQLITE_ROW ){
126126
const char *zCap = db_column_text(&s, 2);
127
- if( strstr(zCap, "s") ) zCap = "s";
128127
@ <tr>
129128
@ <td class="usetupListUser" style="text-align: right;padding-right: 20px;white-space:nowrap;">
130129
if( g.okAdmin && (zCap[0]!='s' || g.okSetup) ){
131130
@ <a href="setup_uedit?id=%d(db_column_int(&s,0))">
132131
}
133132
--- src/setup.c
+++ src/setup.c
@@ -122,11 +122,10 @@
122 @ <th class="usetupListCon" style="text-align: left;">Contact&nbsp;Info</th>
123 @ </tr>
124 db_prepare(&s, "SELECT uid, login, cap, info FROM user ORDER BY login");
125 while( db_step(&s)==SQLITE_ROW ){
126 const char *zCap = db_column_text(&s, 2);
127 if( strstr(zCap, "s") ) zCap = "s";
128 @ <tr>
129 @ <td class="usetupListUser" style="text-align: right;padding-right: 20px;white-space:nowrap;">
130 if( g.okAdmin && (zCap[0]!='s' || g.okSetup) ){
131 @ <a href="setup_uedit?id=%d(db_column_int(&s,0))">
132 }
133
--- src/setup.c
+++ src/setup.c
@@ -122,11 +122,10 @@
122 @ <th class="usetupListCon" style="text-align: left;">Contact&nbsp;Info</th>
123 @ </tr>
124 db_prepare(&s, "SELECT uid, login, cap, info FROM user ORDER BY login");
125 while( db_step(&s)==SQLITE_ROW ){
126 const char *zCap = db_column_text(&s, 2);
 
127 @ <tr>
128 @ <td class="usetupListUser" style="text-align: right;padding-right: 20px;white-space:nowrap;">
129 if( g.okAdmin && (zCap[0]!='s' || g.okSetup) ){
130 @ <a href="setup_uedit?id=%d(db_column_int(&s,0))">
131 }
132
+38 -24
--- src/xfer.c
+++ src/xfer.c
@@ -38,11 +38,11 @@
3838
int nDeltaSent; /* Number of deltas sent */
3939
int nFileRcvd; /* Number of files received */
4040
int nDeltaRcvd; /* Number of deltas received */
4141
int nDanglingFile; /* Number of dangling deltas received */
4242
int mxSend; /* Stop sending "file" with pOut reaches this size */
43
- u8 sendPrivate; /* True to enable sending private content */
43
+ u8 syncPrivate; /* True to enable syncing private content */
4444
u8 nextIsPrivate; /* If true, next "file" received is a private */
4545
};
4646
4747
4848
/*
@@ -261,10 +261,11 @@
261261
** Never send a delta against a private artifact.
262262
*/
263263
static int send_delta_parent(
264264
Xfer *pXfer, /* The transfer context */
265265
int rid, /* record id of the file to send */
266
+ int isPrivate, /* True if rid is a private artifact */
266267
Blob *pContent, /* The content of the file to send */
267268
Blob *pUuid /* The UUID of the file to send */
268269
){
269270
static const char *azQuery[] = {
270271
"SELECT pid FROM plink x"
@@ -285,19 +286,23 @@
285286
int srcId = 0;
286287
287288
for(i=0; srcId==0 && i<count(azQuery); i++){
288289
srcId = db_int(0, azQuery[i], rid);
289290
}
290
- if( srcId>0 && !content_is_private(srcId) && content_get(srcId, &src) ){
291
+ if( srcId>0
292
+ && (pXfer->syncPrivate || !content_is_private(srcId))
293
+ && content_get(srcId, &src)
294
+ ){
291295
char *zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", srcId);
292296
blob_delta_create(&src, pContent, &delta);
293297
size = blob_size(&delta);
294298
if( size>=blob_size(pContent)-50 ){
295299
size = 0;
296300
}else if( uuid_is_shunned(zUuid) ){
297301
size = 0;
298302
}else{
303
+ if( isPrivate ) blob_append(pXfer->pOut, "private\n", -1);
299304
blob_appendf(pXfer->pOut, "file %b %s %d\n", pUuid, zUuid, size);
300305
blob_append(pXfer->pOut, blob_buffer(&delta), size);
301306
/* blob_appendf(pXfer->pOut, "\n", 1); */
302307
}
303308
blob_reset(&delta);
@@ -316,27 +321,31 @@
316321
** Never send a delta against a private artifact.
317322
*/
318323
static int send_delta_native(
319324
Xfer *pXfer, /* The transfer context */
320325
int rid, /* record id of the file to send */
326
+ int isPrivate, /* True if rid is a private artifact */
321327
Blob *pUuid /* The UUID of the file to send */
322328
){
323329
Blob src, delta;
324330
int size = 0;
325331
int srcId;
326332
327333
srcId = db_int(0, "SELECT srcid FROM delta WHERE rid=%d", rid);
328
- if( srcId>0 && !content_is_private(srcId) ){
334
+ if( srcId>0
335
+ && (pXfer->syncPrivate || !content_is_private(srcId))
336
+ ){
329337
blob_zero(&src);
330338
db_blob(&src, "SELECT uuid FROM blob WHERE rid=%d", srcId);
331339
if( uuid_is_shunned(blob_str(&src)) ){
332340
blob_reset(&src);
333341
return 0;
334342
}
335343
blob_zero(&delta);
336344
db_blob(&delta, "SELECT content FROM blob WHERE rid=%d", rid);
337345
blob_uncompress(&delta, &delta);
346
+ if( isPrivate ) blob_append(pXfer->pOut, "private\n", -1);
338347
blob_appendf(pXfer->pOut, "file %b %b %d\n",
339348
pUuid, &src, blob_size(&delta));
340349
blob_append(pXfer->pOut, blob_buffer(&delta), blob_size(&delta));
341350
size = blob_size(&delta);
342351
blob_reset(&delta);
@@ -361,12 +370,13 @@
361370
** this routine becomes a no-op.
362371
*/
363372
static void send_file(Xfer *pXfer, int rid, Blob *pUuid, int nativeDelta){
364373
Blob content, uuid;
365374
int size = 0;
375
+ int isPriv = content_is_private(rid);
366376
367
- if( content_is_private(rid) ) return;
377
+ if( pXfer->syncPrivate==0 && isPriv ) return;
368378
if( db_exists("SELECT 1 FROM onremote WHERE rid=%d", rid) ){
369379
return;
370380
}
371381
blob_zero(&uuid);
372382
db_blob(&uuid, "SELECT uuid FROM blob WHERE rid=%d AND size>=0", rid);
@@ -384,29 +394,31 @@
384394
if( uuid_is_shunned(blob_str(pUuid)) ){
385395
blob_reset(&uuid);
386396
return;
387397
}
388398
if( pXfer->mxSend<=blob_size(pXfer->pOut) ){
389
- blob_appendf(pXfer->pOut, "igot %b\n", pUuid);
399
+ const char *zFormat = isPriv ? "igot %b 1\n" : "igot %b\n";
400
+ blob_appendf(pXfer->pOut, zFormat, pUuid);
390401
pXfer->nIGotSent++;
391402
blob_reset(&uuid);
392403
return;
393404
}
394405
if( nativeDelta ){
395
- size = send_delta_native(pXfer, rid, pUuid);
406
+ size = send_delta_native(pXfer, rid, isPriv, pUuid);
396407
if( size ){
397408
pXfer->nDeltaSent++;
398409
}
399410
}
400411
if( size==0 ){
401412
content_get(rid, &content);
402413
403414
if( !nativeDelta && blob_size(&content)>100 ){
404
- size = send_delta_parent(pXfer, rid, &content, pUuid);
415
+ size = send_delta_parent(pXfer, rid, isPriv, &content, pUuid);
405416
}
406417
if( size==0 ){
407418
int size = blob_size(&content);
419
+ if( isPriv ) blob_append(pXfer->pOut, "private\n", -1);
408420
blob_appendf(pXfer->pOut, "file %b %d\n", pUuid, size);
409421
blob_append(pXfer->pOut, blob_buffer(&content), size);
410422
pXfer->nFileSent++;
411423
}else{
412424
pXfer->nDeltaSent++;
@@ -426,33 +438,35 @@
426438
const char *zUuid;
427439
const char *zDelta;
428440
int szU;
429441
int szC;
430442
int rc;
443
+ int isPrivate;
431444
static Stmt q1;
432445
446
+ isPrivate = content_is_private(rid);
447
+ if( isPrivate && pXfer->syncPrivate==0 ) return;
433448
db_static_prepare(&q1,
434449
"SELECT uuid, size, content,"
435450
" (SELECT uuid FROM delta, blob"
436451
" WHERE delta.rid=:rid AND delta.srcid=blob.rid)"
437452
" FROM blob"
438453
" WHERE rid=:rid"
439454
" AND size>=0"
440455
" AND uuid NOT IN shun"
441
- " AND rid NOT IN private",
442
- rid
443456
);
444457
db_bind_int(&q1, ":rid", rid);
445458
rc = db_step(&q1);
446459
if( rc==SQLITE_ROW ){
447460
zUuid = db_column_text(&q1, 0);
448461
szU = db_column_int(&q1, 1);
449462
szC = db_column_bytes(&q1, 2);
450463
zContent = db_column_raw(&q1, 2);
451464
zDelta = db_column_text(&q1, 3);
465
+ if( isPrivate ) blob_append(pXfer->pOut, "private\n", -1);
452466
blob_appendf(pXfer->pOut, "cfile %s ", zUuid);
453
- if( zDelta ){
467
+ if( zDelta ){
454468
blob_appendf(pXfer->pOut, "%s ", zDelta);
455469
pXfer->nDeltaSent++;
456470
}else{
457471
pXfer->nFileSent++;
458472
}
@@ -472,11 +486,11 @@
472486
static void request_phantoms(Xfer *pXfer, int maxReq){
473487
Stmt q;
474488
db_prepare(&q,
475489
"SELECT uuid FROM phantom JOIN blob USING(rid)"
476490
" WHERE NOT EXISTS(SELECT 1 FROM shun WHERE uuid=blob.uuid) %s",
477
- (pXfer->sendPrivate ? "" :
491
+ (pXfer->syncPrivate ? "" :
478492
" AND NOT EXISTS(SELECT 1 FROM private WHERE rid=blob.rid)")
479493
);
480494
while( db_step(&q)==SQLITE_ROW && maxReq-- > 0 ){
481495
const char *zUuid = db_column_text(&q, 0);
482496
blob_appendf(pXfer->pOut, "gimme %s\n", zUuid);
@@ -668,11 +682,11 @@
668682
** Send igot messages for every private artifact
669683
*/
670684
static int send_private(Xfer *pXfer){
671685
int cnt = 0;
672686
Stmt q;
673
- if( pXfer->sendPrivate ){
687
+ if( pXfer->syncPrivate ){
674688
db_prepare(&q, "SELECT uuid FROM private JOIN blob USING(rid)");
675689
while( db_step(&q)==SQLITE_ROW ){
676690
blob_appendf(pXfer->pOut, "igot %s 1\n", db_column_text(&q,0));
677691
cnt++;
678692
}
@@ -1088,19 +1102,19 @@
10881102
**
10891103
** The client issue pragmas to try to influence the behavior of the
10901104
** server. These are requests only. Unknown pragmas are silently
10911105
** ignored.
10921106
*/
1093
- if( blob_eq(&xfer.aToken[0], "set") && xfer.nToken>=2 ){
1107
+ if( blob_eq(&xfer.aToken[0], "pragma") && xfer.nToken>=2 ){
10941108
/* pragma send-private
10951109
**
10961110
** If the user has the "x" privilege (which must be set explicitly -
10971111
** it is not automatic with "a" or "s") then this pragma causes
10981112
** private information to be pulled in addition to public records.
10991113
*/
11001114
if( blob_eq(&xfer.aToken[1], "send-private") ){
1101
- if( g.okPrivate ) xfer.sendPrivate = 1;
1115
+ if( g.okPrivate ) xfer.syncPrivate = 1;
11021116
}
11031117
}else
11041118
11051119
/* Unknown message
11061120
*/
@@ -1120,15 +1134,15 @@
11201134
** cause the client to create phantoms for all artifacts, which will
11211135
** in turn make sure that the entire repository is sent efficiently
11221136
** and expeditiously.
11231137
*/
11241138
send_all(&xfer);
1125
- if( xfer.sendPrivate ) send_private(&xfer);
1139
+ if( xfer.syncPrivate ) send_private(&xfer);
11261140
}else if( isPull ){
11271141
create_cluster();
11281142
send_unclustered(&xfer);
1129
- if( xfer.sendPrivate ) send_private(&xfer);
1143
+ if( xfer.syncPrivate ) send_private(&xfer);
11301144
}
11311145
if( recvConfig ){
11321146
configure_finalize_receive();
11331147
}
11341148
manifest_crosslink_end();
@@ -1231,11 +1245,11 @@
12311245
xfer.pIn = &recv;
12321246
xfer.pOut = &send;
12331247
xfer.mxSend = db_get_int("max-upload", 250000);
12341248
if( privateFlag ){
12351249
g.okPrivate = 1;
1236
- xfer.sendPrivate = 1;
1250
+ xfer.syncPrivate = 1;
12371251
}
12381252
12391253
assert( pushFlag | pullFlag | cloneFlag | configRcvMask | configSendMask );
12401254
db_begin_transaction();
12411255
db_record_repository_filename(0);
@@ -1247,10 +1261,14 @@
12471261
blob_zero(&recv);
12481262
blob_zero(&xfer.err);
12491263
blob_zero(&xfer.line);
12501264
origConfigRcvMask = 0;
12511265
1266
+
1267
+ /* Send the send-private pragma if we are trying to sync private data */
1268
+ if( privateFlag ) blob_append(&send, "pragma send-private\n", -1);
1269
+
12521270
/*
12531271
** Always begin with a clone, pull, or push message
12541272
*/
12551273
if( cloneFlag ){
12561274
blob_appendf(&send, "clone 3 %d\n", cloneSeqno);
@@ -1281,17 +1299,10 @@
12811299
zCookie = db_get("cookie", 0);
12821300
if( zCookie ){
12831301
blob_appendf(&send, "cookie %s\n", zCookie);
12841302
}
12851303
1286
- /* Send a pragma to alert the server that we want private content if
1287
- ** doing a private push, pull, sync, or clone.
1288
- */
1289
- if( privateFlag ){
1290
- blob_append(&send, "pragma send-private\n", -1);
1291
- }
1292
-
12931304
/* Generate gimme cards for phantoms and leaf cards
12941305
** for all leaves.
12951306
*/
12961307
if( pullFlag || (cloneFlag && cloneSeqno==1) ){
12971308
request_phantoms(&xfer, mxPhantomReq);
@@ -1360,10 +1371,13 @@
13601371
break;
13611372
}
13621373
lastPctDone = -1;
13631374
blob_reset(&send);
13641375
rArrivalTime = db_double(0.0, "SELECT julianday('now')");
1376
+
1377
+ /* Send the send-private pragma if we are trying to sync private data */
1378
+ if( privateFlag ) blob_append(&send, "pragma send-private\n", -1);
13651379
13661380
/* Begin constructing the next message (which might never be
13671381
** sent) by beginning with the pull or push cards
13681382
*/
13691383
if( pullFlag ){
13701384
--- src/xfer.c
+++ src/xfer.c
@@ -38,11 +38,11 @@
38 int nDeltaSent; /* Number of deltas sent */
39 int nFileRcvd; /* Number of files received */
40 int nDeltaRcvd; /* Number of deltas received */
41 int nDanglingFile; /* Number of dangling deltas received */
42 int mxSend; /* Stop sending "file" with pOut reaches this size */
43 u8 sendPrivate; /* True to enable sending private content */
44 u8 nextIsPrivate; /* If true, next "file" received is a private */
45 };
46
47
48 /*
@@ -261,10 +261,11 @@
261 ** Never send a delta against a private artifact.
262 */
263 static int send_delta_parent(
264 Xfer *pXfer, /* The transfer context */
265 int rid, /* record id of the file to send */
 
266 Blob *pContent, /* The content of the file to send */
267 Blob *pUuid /* The UUID of the file to send */
268 ){
269 static const char *azQuery[] = {
270 "SELECT pid FROM plink x"
@@ -285,19 +286,23 @@
285 int srcId = 0;
286
287 for(i=0; srcId==0 && i<count(azQuery); i++){
288 srcId = db_int(0, azQuery[i], rid);
289 }
290 if( srcId>0 && !content_is_private(srcId) && content_get(srcId, &src) ){
 
 
 
291 char *zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", srcId);
292 blob_delta_create(&src, pContent, &delta);
293 size = blob_size(&delta);
294 if( size>=blob_size(pContent)-50 ){
295 size = 0;
296 }else if( uuid_is_shunned(zUuid) ){
297 size = 0;
298 }else{
 
299 blob_appendf(pXfer->pOut, "file %b %s %d\n", pUuid, zUuid, size);
300 blob_append(pXfer->pOut, blob_buffer(&delta), size);
301 /* blob_appendf(pXfer->pOut, "\n", 1); */
302 }
303 blob_reset(&delta);
@@ -316,27 +321,31 @@
316 ** Never send a delta against a private artifact.
317 */
318 static int send_delta_native(
319 Xfer *pXfer, /* The transfer context */
320 int rid, /* record id of the file to send */
 
321 Blob *pUuid /* The UUID of the file to send */
322 ){
323 Blob src, delta;
324 int size = 0;
325 int srcId;
326
327 srcId = db_int(0, "SELECT srcid FROM delta WHERE rid=%d", rid);
328 if( srcId>0 && !content_is_private(srcId) ){
 
 
329 blob_zero(&src);
330 db_blob(&src, "SELECT uuid FROM blob WHERE rid=%d", srcId);
331 if( uuid_is_shunned(blob_str(&src)) ){
332 blob_reset(&src);
333 return 0;
334 }
335 blob_zero(&delta);
336 db_blob(&delta, "SELECT content FROM blob WHERE rid=%d", rid);
337 blob_uncompress(&delta, &delta);
 
338 blob_appendf(pXfer->pOut, "file %b %b %d\n",
339 pUuid, &src, blob_size(&delta));
340 blob_append(pXfer->pOut, blob_buffer(&delta), blob_size(&delta));
341 size = blob_size(&delta);
342 blob_reset(&delta);
@@ -361,12 +370,13 @@
361 ** this routine becomes a no-op.
362 */
363 static void send_file(Xfer *pXfer, int rid, Blob *pUuid, int nativeDelta){
364 Blob content, uuid;
365 int size = 0;
 
366
367 if( content_is_private(rid) ) return;
368 if( db_exists("SELECT 1 FROM onremote WHERE rid=%d", rid) ){
369 return;
370 }
371 blob_zero(&uuid);
372 db_blob(&uuid, "SELECT uuid FROM blob WHERE rid=%d AND size>=0", rid);
@@ -384,29 +394,31 @@
384 if( uuid_is_shunned(blob_str(pUuid)) ){
385 blob_reset(&uuid);
386 return;
387 }
388 if( pXfer->mxSend<=blob_size(pXfer->pOut) ){
389 blob_appendf(pXfer->pOut, "igot %b\n", pUuid);
 
390 pXfer->nIGotSent++;
391 blob_reset(&uuid);
392 return;
393 }
394 if( nativeDelta ){
395 size = send_delta_native(pXfer, rid, pUuid);
396 if( size ){
397 pXfer->nDeltaSent++;
398 }
399 }
400 if( size==0 ){
401 content_get(rid, &content);
402
403 if( !nativeDelta && blob_size(&content)>100 ){
404 size = send_delta_parent(pXfer, rid, &content, pUuid);
405 }
406 if( size==0 ){
407 int size = blob_size(&content);
 
408 blob_appendf(pXfer->pOut, "file %b %d\n", pUuid, size);
409 blob_append(pXfer->pOut, blob_buffer(&content), size);
410 pXfer->nFileSent++;
411 }else{
412 pXfer->nDeltaSent++;
@@ -426,33 +438,35 @@
426 const char *zUuid;
427 const char *zDelta;
428 int szU;
429 int szC;
430 int rc;
 
431 static Stmt q1;
432
 
 
433 db_static_prepare(&q1,
434 "SELECT uuid, size, content,"
435 " (SELECT uuid FROM delta, blob"
436 " WHERE delta.rid=:rid AND delta.srcid=blob.rid)"
437 " FROM blob"
438 " WHERE rid=:rid"
439 " AND size>=0"
440 " AND uuid NOT IN shun"
441 " AND rid NOT IN private",
442 rid
443 );
444 db_bind_int(&q1, ":rid", rid);
445 rc = db_step(&q1);
446 if( rc==SQLITE_ROW ){
447 zUuid = db_column_text(&q1, 0);
448 szU = db_column_int(&q1, 1);
449 szC = db_column_bytes(&q1, 2);
450 zContent = db_column_raw(&q1, 2);
451 zDelta = db_column_text(&q1, 3);
 
452 blob_appendf(pXfer->pOut, "cfile %s ", zUuid);
453 if( zDelta ){
454 blob_appendf(pXfer->pOut, "%s ", zDelta);
455 pXfer->nDeltaSent++;
456 }else{
457 pXfer->nFileSent++;
458 }
@@ -472,11 +486,11 @@
472 static void request_phantoms(Xfer *pXfer, int maxReq){
473 Stmt q;
474 db_prepare(&q,
475 "SELECT uuid FROM phantom JOIN blob USING(rid)"
476 " WHERE NOT EXISTS(SELECT 1 FROM shun WHERE uuid=blob.uuid) %s",
477 (pXfer->sendPrivate ? "" :
478 " AND NOT EXISTS(SELECT 1 FROM private WHERE rid=blob.rid)")
479 );
480 while( db_step(&q)==SQLITE_ROW && maxReq-- > 0 ){
481 const char *zUuid = db_column_text(&q, 0);
482 blob_appendf(pXfer->pOut, "gimme %s\n", zUuid);
@@ -668,11 +682,11 @@
668 ** Send igot messages for every private artifact
669 */
670 static int send_private(Xfer *pXfer){
671 int cnt = 0;
672 Stmt q;
673 if( pXfer->sendPrivate ){
674 db_prepare(&q, "SELECT uuid FROM private JOIN blob USING(rid)");
675 while( db_step(&q)==SQLITE_ROW ){
676 blob_appendf(pXfer->pOut, "igot %s 1\n", db_column_text(&q,0));
677 cnt++;
678 }
@@ -1088,19 +1102,19 @@
1088 **
1089 ** The client issue pragmas to try to influence the behavior of the
1090 ** server. These are requests only. Unknown pragmas are silently
1091 ** ignored.
1092 */
1093 if( blob_eq(&xfer.aToken[0], "set") && xfer.nToken>=2 ){
1094 /* pragma send-private
1095 **
1096 ** If the user has the "x" privilege (which must be set explicitly -
1097 ** it is not automatic with "a" or "s") then this pragma causes
1098 ** private information to be pulled in addition to public records.
1099 */
1100 if( blob_eq(&xfer.aToken[1], "send-private") ){
1101 if( g.okPrivate ) xfer.sendPrivate = 1;
1102 }
1103 }else
1104
1105 /* Unknown message
1106 */
@@ -1120,15 +1134,15 @@
1120 ** cause the client to create phantoms for all artifacts, which will
1121 ** in turn make sure that the entire repository is sent efficiently
1122 ** and expeditiously.
1123 */
1124 send_all(&xfer);
1125 if( xfer.sendPrivate ) send_private(&xfer);
1126 }else if( isPull ){
1127 create_cluster();
1128 send_unclustered(&xfer);
1129 if( xfer.sendPrivate ) send_private(&xfer);
1130 }
1131 if( recvConfig ){
1132 configure_finalize_receive();
1133 }
1134 manifest_crosslink_end();
@@ -1231,11 +1245,11 @@
1231 xfer.pIn = &recv;
1232 xfer.pOut = &send;
1233 xfer.mxSend = db_get_int("max-upload", 250000);
1234 if( privateFlag ){
1235 g.okPrivate = 1;
1236 xfer.sendPrivate = 1;
1237 }
1238
1239 assert( pushFlag | pullFlag | cloneFlag | configRcvMask | configSendMask );
1240 db_begin_transaction();
1241 db_record_repository_filename(0);
@@ -1247,10 +1261,14 @@
1247 blob_zero(&recv);
1248 blob_zero(&xfer.err);
1249 blob_zero(&xfer.line);
1250 origConfigRcvMask = 0;
1251
 
 
 
 
1252 /*
1253 ** Always begin with a clone, pull, or push message
1254 */
1255 if( cloneFlag ){
1256 blob_appendf(&send, "clone 3 %d\n", cloneSeqno);
@@ -1281,17 +1299,10 @@
1281 zCookie = db_get("cookie", 0);
1282 if( zCookie ){
1283 blob_appendf(&send, "cookie %s\n", zCookie);
1284 }
1285
1286 /* Send a pragma to alert the server that we want private content if
1287 ** doing a private push, pull, sync, or clone.
1288 */
1289 if( privateFlag ){
1290 blob_append(&send, "pragma send-private\n", -1);
1291 }
1292
1293 /* Generate gimme cards for phantoms and leaf cards
1294 ** for all leaves.
1295 */
1296 if( pullFlag || (cloneFlag && cloneSeqno==1) ){
1297 request_phantoms(&xfer, mxPhantomReq);
@@ -1360,10 +1371,13 @@
1360 break;
1361 }
1362 lastPctDone = -1;
1363 blob_reset(&send);
1364 rArrivalTime = db_double(0.0, "SELECT julianday('now')");
 
 
 
1365
1366 /* Begin constructing the next message (which might never be
1367 ** sent) by beginning with the pull or push cards
1368 */
1369 if( pullFlag ){
1370
--- src/xfer.c
+++ src/xfer.c
@@ -38,11 +38,11 @@
38 int nDeltaSent; /* Number of deltas sent */
39 int nFileRcvd; /* Number of files received */
40 int nDeltaRcvd; /* Number of deltas received */
41 int nDanglingFile; /* Number of dangling deltas received */
42 int mxSend; /* Stop sending "file" with pOut reaches this size */
43 u8 syncPrivate; /* True to enable syncing private content */
44 u8 nextIsPrivate; /* If true, next "file" received is a private */
45 };
46
47
48 /*
@@ -261,10 +261,11 @@
261 ** Never send a delta against a private artifact.
262 */
263 static int send_delta_parent(
264 Xfer *pXfer, /* The transfer context */
265 int rid, /* record id of the file to send */
266 int isPrivate, /* True if rid is a private artifact */
267 Blob *pContent, /* The content of the file to send */
268 Blob *pUuid /* The UUID of the file to send */
269 ){
270 static const char *azQuery[] = {
271 "SELECT pid FROM plink x"
@@ -285,19 +286,23 @@
286 int srcId = 0;
287
288 for(i=0; srcId==0 && i<count(azQuery); i++){
289 srcId = db_int(0, azQuery[i], rid);
290 }
291 if( srcId>0
292 && (pXfer->syncPrivate || !content_is_private(srcId))
293 && content_get(srcId, &src)
294 ){
295 char *zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", srcId);
296 blob_delta_create(&src, pContent, &delta);
297 size = blob_size(&delta);
298 if( size>=blob_size(pContent)-50 ){
299 size = 0;
300 }else if( uuid_is_shunned(zUuid) ){
301 size = 0;
302 }else{
303 if( isPrivate ) blob_append(pXfer->pOut, "private\n", -1);
304 blob_appendf(pXfer->pOut, "file %b %s %d\n", pUuid, zUuid, size);
305 blob_append(pXfer->pOut, blob_buffer(&delta), size);
306 /* blob_appendf(pXfer->pOut, "\n", 1); */
307 }
308 blob_reset(&delta);
@@ -316,27 +321,31 @@
321 ** Never send a delta against a private artifact.
322 */
323 static int send_delta_native(
324 Xfer *pXfer, /* The transfer context */
325 int rid, /* record id of the file to send */
326 int isPrivate, /* True if rid is a private artifact */
327 Blob *pUuid /* The UUID of the file to send */
328 ){
329 Blob src, delta;
330 int size = 0;
331 int srcId;
332
333 srcId = db_int(0, "SELECT srcid FROM delta WHERE rid=%d", rid);
334 if( srcId>0
335 && (pXfer->syncPrivate || !content_is_private(srcId))
336 ){
337 blob_zero(&src);
338 db_blob(&src, "SELECT uuid FROM blob WHERE rid=%d", srcId);
339 if( uuid_is_shunned(blob_str(&src)) ){
340 blob_reset(&src);
341 return 0;
342 }
343 blob_zero(&delta);
344 db_blob(&delta, "SELECT content FROM blob WHERE rid=%d", rid);
345 blob_uncompress(&delta, &delta);
346 if( isPrivate ) blob_append(pXfer->pOut, "private\n", -1);
347 blob_appendf(pXfer->pOut, "file %b %b %d\n",
348 pUuid, &src, blob_size(&delta));
349 blob_append(pXfer->pOut, blob_buffer(&delta), blob_size(&delta));
350 size = blob_size(&delta);
351 blob_reset(&delta);
@@ -361,12 +370,13 @@
370 ** this routine becomes a no-op.
371 */
372 static void send_file(Xfer *pXfer, int rid, Blob *pUuid, int nativeDelta){
373 Blob content, uuid;
374 int size = 0;
375 int isPriv = content_is_private(rid);
376
377 if( pXfer->syncPrivate==0 && isPriv ) return;
378 if( db_exists("SELECT 1 FROM onremote WHERE rid=%d", rid) ){
379 return;
380 }
381 blob_zero(&uuid);
382 db_blob(&uuid, "SELECT uuid FROM blob WHERE rid=%d AND size>=0", rid);
@@ -384,29 +394,31 @@
394 if( uuid_is_shunned(blob_str(pUuid)) ){
395 blob_reset(&uuid);
396 return;
397 }
398 if( pXfer->mxSend<=blob_size(pXfer->pOut) ){
399 const char *zFormat = isPriv ? "igot %b 1\n" : "igot %b\n";
400 blob_appendf(pXfer->pOut, zFormat, pUuid);
401 pXfer->nIGotSent++;
402 blob_reset(&uuid);
403 return;
404 }
405 if( nativeDelta ){
406 size = send_delta_native(pXfer, rid, isPriv, pUuid);
407 if( size ){
408 pXfer->nDeltaSent++;
409 }
410 }
411 if( size==0 ){
412 content_get(rid, &content);
413
414 if( !nativeDelta && blob_size(&content)>100 ){
415 size = send_delta_parent(pXfer, rid, isPriv, &content, pUuid);
416 }
417 if( size==0 ){
418 int size = blob_size(&content);
419 if( isPriv ) blob_append(pXfer->pOut, "private\n", -1);
420 blob_appendf(pXfer->pOut, "file %b %d\n", pUuid, size);
421 blob_append(pXfer->pOut, blob_buffer(&content), size);
422 pXfer->nFileSent++;
423 }else{
424 pXfer->nDeltaSent++;
@@ -426,33 +438,35 @@
438 const char *zUuid;
439 const char *zDelta;
440 int szU;
441 int szC;
442 int rc;
443 int isPrivate;
444 static Stmt q1;
445
446 isPrivate = content_is_private(rid);
447 if( isPrivate && pXfer->syncPrivate==0 ) return;
448 db_static_prepare(&q1,
449 "SELECT uuid, size, content,"
450 " (SELECT uuid FROM delta, blob"
451 " WHERE delta.rid=:rid AND delta.srcid=blob.rid)"
452 " FROM blob"
453 " WHERE rid=:rid"
454 " AND size>=0"
455 " AND uuid NOT IN shun"
 
 
456 );
457 db_bind_int(&q1, ":rid", rid);
458 rc = db_step(&q1);
459 if( rc==SQLITE_ROW ){
460 zUuid = db_column_text(&q1, 0);
461 szU = db_column_int(&q1, 1);
462 szC = db_column_bytes(&q1, 2);
463 zContent = db_column_raw(&q1, 2);
464 zDelta = db_column_text(&q1, 3);
465 if( isPrivate ) blob_append(pXfer->pOut, "private\n", -1);
466 blob_appendf(pXfer->pOut, "cfile %s ", zUuid);
467 if( zDelta ){
468 blob_appendf(pXfer->pOut, "%s ", zDelta);
469 pXfer->nDeltaSent++;
470 }else{
471 pXfer->nFileSent++;
472 }
@@ -472,11 +486,11 @@
486 static void request_phantoms(Xfer *pXfer, int maxReq){
487 Stmt q;
488 db_prepare(&q,
489 "SELECT uuid FROM phantom JOIN blob USING(rid)"
490 " WHERE NOT EXISTS(SELECT 1 FROM shun WHERE uuid=blob.uuid) %s",
491 (pXfer->syncPrivate ? "" :
492 " AND NOT EXISTS(SELECT 1 FROM private WHERE rid=blob.rid)")
493 );
494 while( db_step(&q)==SQLITE_ROW && maxReq-- > 0 ){
495 const char *zUuid = db_column_text(&q, 0);
496 blob_appendf(pXfer->pOut, "gimme %s\n", zUuid);
@@ -668,11 +682,11 @@
682 ** Send igot messages for every private artifact
683 */
684 static int send_private(Xfer *pXfer){
685 int cnt = 0;
686 Stmt q;
687 if( pXfer->syncPrivate ){
688 db_prepare(&q, "SELECT uuid FROM private JOIN blob USING(rid)");
689 while( db_step(&q)==SQLITE_ROW ){
690 blob_appendf(pXfer->pOut, "igot %s 1\n", db_column_text(&q,0));
691 cnt++;
692 }
@@ -1088,19 +1102,19 @@
1102 **
1103 ** The client issue pragmas to try to influence the behavior of the
1104 ** server. These are requests only. Unknown pragmas are silently
1105 ** ignored.
1106 */
1107 if( blob_eq(&xfer.aToken[0], "pragma") && xfer.nToken>=2 ){
1108 /* pragma send-private
1109 **
1110 ** If the user has the "x" privilege (which must be set explicitly -
1111 ** it is not automatic with "a" or "s") then this pragma causes
1112 ** private information to be pulled in addition to public records.
1113 */
1114 if( blob_eq(&xfer.aToken[1], "send-private") ){
1115 if( g.okPrivate ) xfer.syncPrivate = 1;
1116 }
1117 }else
1118
1119 /* Unknown message
1120 */
@@ -1120,15 +1134,15 @@
1134 ** cause the client to create phantoms for all artifacts, which will
1135 ** in turn make sure that the entire repository is sent efficiently
1136 ** and expeditiously.
1137 */
1138 send_all(&xfer);
1139 if( xfer.syncPrivate ) send_private(&xfer);
1140 }else if( isPull ){
1141 create_cluster();
1142 send_unclustered(&xfer);
1143 if( xfer.syncPrivate ) send_private(&xfer);
1144 }
1145 if( recvConfig ){
1146 configure_finalize_receive();
1147 }
1148 manifest_crosslink_end();
@@ -1231,11 +1245,11 @@
1245 xfer.pIn = &recv;
1246 xfer.pOut = &send;
1247 xfer.mxSend = db_get_int("max-upload", 250000);
1248 if( privateFlag ){
1249 g.okPrivate = 1;
1250 xfer.syncPrivate = 1;
1251 }
1252
1253 assert( pushFlag | pullFlag | cloneFlag | configRcvMask | configSendMask );
1254 db_begin_transaction();
1255 db_record_repository_filename(0);
@@ -1247,10 +1261,14 @@
1261 blob_zero(&recv);
1262 blob_zero(&xfer.err);
1263 blob_zero(&xfer.line);
1264 origConfigRcvMask = 0;
1265
1266
1267 /* Send the send-private pragma if we are trying to sync private data */
1268 if( privateFlag ) blob_append(&send, "pragma send-private\n", -1);
1269
1270 /*
1271 ** Always begin with a clone, pull, or push message
1272 */
1273 if( cloneFlag ){
1274 blob_appendf(&send, "clone 3 %d\n", cloneSeqno);
@@ -1281,17 +1299,10 @@
1299 zCookie = db_get("cookie", 0);
1300 if( zCookie ){
1301 blob_appendf(&send, "cookie %s\n", zCookie);
1302 }
1303
 
 
 
 
 
 
 
1304 /* Generate gimme cards for phantoms and leaf cards
1305 ** for all leaves.
1306 */
1307 if( pullFlag || (cloneFlag && cloneSeqno==1) ){
1308 request_phantoms(&xfer, mxPhantomReq);
@@ -1360,10 +1371,13 @@
1371 break;
1372 }
1373 lastPctDone = -1;
1374 blob_reset(&send);
1375 rArrivalTime = db_double(0.0, "SELECT julianday('now')");
1376
1377 /* Send the send-private pragma if we are trying to sync private data */
1378 if( privateFlag ) blob_append(&send, "pragma send-private\n", -1);
1379
1380 /* Begin constructing the next message (which might never be
1381 ** sent) by beginning with the pull or push cards
1382 */
1383 if( pullFlag ){
1384

Keyboard Shortcuts

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