Many hyperlinks are disabled.
Use anonymous login
to enable hyperlinks.
Overview
| Comment: | Change the definition of a "Leaf" to be any node that has no children of any kind (merge or non-merge) in the same branch. A "rebuild" or a "fossil leaves --recompute" is required to recompute the LEAF table after upgrading to this version. |
|---|---|
| Downloads: | Tarball | ZIP archive |
| Timelines: | family | ancestors | descendants | both | trunk |
| Files: | files | file ages | folders |
| SHA1: |
e17fc71319e0534b3c5bf2df9754bc69 |
| User & Date: | drh 2011-04-25 22:23:56.886 |
Context
|
2011-04-27
| ||
| 02:10 | Merge in the config-sync changes. This is a major schema change and definitely requires a "fossil rebuild". Note that the schema upgrade is irreversible and so you should be certain you want to continue with the new schema before you upgrade. check-in: 1654456ef5 user: drh tags: trunk | |
|
2011-04-26
| ||
| 00:45 | Begin implementing the protocol changes for configuration sync. check-in: f99e3fa9e6 user: drh tags: config-sync | |
|
2011-04-25
| ||
| 22:23 | Change the definition of a "Leaf" to be any node that has no children of any kind (merge or non-merge) in the same branch. A "rebuild" or a "fossil leaves --recompute" is required to recompute the LEAF table after upgrading to this version. check-in: e17fc71319 user: drh tags: trunk | |
| 20:26 | Add hyperlink to the annotation of a file in the object description header. check-in: 030a048697 user: drh tags: trunk | |
Changes
Changes to src/checkin.c.
| ︙ | ︙ | |||
464 465 466 467 468 469 470 |
g.aCommitFile[ii-2] = iId;
blob_reset(&b);
}
g.aCommitFile[ii-2] = 0;
}
}
| < < < < < < < < < < < < < < < < < < < | 464 465 466 467 468 469 470 471 472 473 474 475 476 477 |
g.aCommitFile[ii-2] = iId;
blob_reset(&b);
}
g.aCommitFile[ii-2] = 0;
}
}
/*
** Make sure the current check-in with timestamp zDate is younger than its
** ancestor identified rid and zUuid. Throw a fatal error if not.
*/
static void checkin_verify_younger(
int rid, /* The record ID of the ancestor */
const char *zUuid, /* The artifact ID of the ancestor */
|
| ︙ | ︙ |
Changes to src/graph.c.
| ︙ | ︙ | |||
420 421 422 423 424 425 426 |
*/
inUse = (1<<(p->mxRail+1))-1;
for(pRow=p->pLast; pRow; pRow=pRow->pPrev){
int parentRid;
if( pRow->iRail>=0 ){
if( pRow->pChild==0 && !pRow->timeWarp ){
| | | 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 |
*/
inUse = (1<<(p->mxRail+1))-1;
for(pRow=p->pLast; pRow; pRow=pRow->pPrev){
int parentRid;
if( pRow->iRail>=0 ){
if( pRow->pChild==0 && !pRow->timeWarp ){
if( omitDescenders || count_nonbranch_children(pRow->rid)==0 ){
inUse &= ~(1<<pRow->iRail);
}else{
pRow->aiRiser[pRow->iRail] = 0;
mask = 1<<pRow->iRail;
for(pLoop=pRow; pLoop; pLoop=pLoop->pPrev){
pLoop->railInUse |= mask;
}
|
| ︙ | ︙ |
Changes to src/info.c.
| ︙ | ︙ | |||
366 367 368 369 370 371 372 |
}
zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
zParent = db_text(0,
"SELECT uuid FROM plink, blob"
" WHERE plink.cid=%d AND blob.rid=plink.pid AND plink.isprim",
rid
);
| | | 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 |
}
zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
zParent = db_text(0,
"SELECT uuid FROM plink, blob"
" WHERE plink.cid=%d AND blob.rid=plink.pid AND plink.isprim",
rid
);
isLeaf = is_a_leaf(rid);
db_prepare(&q,
"SELECT uuid, datetime(mtime, 'localtime'), user, comment,"
" datetime(omtime, 'localtime')"
" FROM blob, event"
" WHERE blob.rid=%d"
" AND event.objid=%d",
rid, rid
|
| ︙ | ︙ |
Changes to src/leaf.c.
| ︙ | ︙ | |||
21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 |
** The LEAF table contains the rids for all leaves in the checkin DAG.
** A leaf is a checkin that has no children in the same branch.
*/
#include "config.h"
#include "leaf.h"
#include <assert.h>
/*
** Recompute the entire LEAF table.
**
** This can be expensive (5 seconds or so) for a really large repository.
** So it is only done for things like a rebuild.
*/
void leaf_rebuild(void){
db_multi_exec(
"DELETE FROM leaf;"
"INSERT OR IGNORE INTO leaf"
" SELECT cid FROM plink"
" EXCEPT"
" SELECT pid FROM plink"
" WHERE coalesce((SELECT value FROM tagxref"
" WHERE tagid=%d AND rid=plink.pid),'trunk')"
" == coalesce((SELECT value FROM tagxref"
| > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > | < | 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 |
** The LEAF table contains the rids for all leaves in the checkin DAG.
** A leaf is a checkin that has no children in the same branch.
*/
#include "config.h"
#include "leaf.h"
#include <assert.h>
/*
** Return true if the check-in with RID=rid is a leaf.
**
** A leaf has no children in the same branch.
*/
int is_a_leaf(int rid){
int rc;
static const char zSql[] =
@ SELECT 1 FROM plink
@ WHERE pid=%d
@ AND coalesce((SELECT value FROM tagxref
@ WHERE tagid=%d AND rid=plink.pid), 'trunk')
@ =coalesce((SELECT value FROM tagxref
@ WHERE tagid=%d AND rid=plink.cid), 'trunk')
;
rc = db_int(0, zSql, rid, TAG_BRANCH, TAG_BRANCH);
return rc==0;
}
/*
** Count the number of primary non-branch children for the given check-in.
**
** A primary child is one where the parent is the primary parent, not
** a merge parent. A "leaf" is a node that has zero children of any
** kind. This routine counts only primary children.
**
** A non-branch child is one which is on the same branch as the parent.
*/
int count_nonbranch_children(int pid){
int nNonBranch = 0;
static Stmt q;
static const char zSql[] =
@ SELECT count(*) FROM plink
@ WHERE pid=:pid AND isprim
@ AND coalesce((SELECT value FROM tagxref
@ WHERE tagid=%d AND rid=plink.pid), 'trunk')
@ =coalesce((SELECT value FROM tagxref
@ WHERE tagid=%d AND rid=plink.cid), 'trunk')
;
db_static_prepare(&q, zSql, TAG_BRANCH, TAG_BRANCH);
db_bind_int(&q, ":pid", pid);
if( db_step(&q)==SQLITE_ROW ){
nNonBranch = db_column_int(&q, 0);
}
db_reset(&q);
return nNonBranch;
}
/*
** Recompute the entire LEAF table.
**
** This can be expensive (5 seconds or so) for a really large repository.
** So it is only done for things like a rebuild.
*/
void leaf_rebuild(void){
db_multi_exec(
"DELETE FROM leaf;"
"INSERT OR IGNORE INTO leaf"
" SELECT cid FROM plink"
" EXCEPT"
" SELECT pid FROM plink"
" WHERE coalesce((SELECT value FROM tagxref"
" WHERE tagid=%d AND rid=plink.pid),'trunk')"
" == coalesce((SELECT value FROM tagxref"
" WHERE tagid=%d AND rid=plink.cid),'trunk')",
TAG_BRANCH, TAG_BRANCH
);
}
/*
** A bag of checkins whose leaf status needs to be checked.
*/
|
| ︙ | ︙ | |||
61 62 63 64 65 66 67 |
static Stmt checkIfLeaf;
static Stmt addLeaf;
static Stmt removeLeaf;
int rc;
db_static_prepare(&checkIfLeaf,
"SELECT 1 FROM plink"
| | | 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 |
static Stmt checkIfLeaf;
static Stmt addLeaf;
static Stmt removeLeaf;
int rc;
db_static_prepare(&checkIfLeaf,
"SELECT 1 FROM plink"
" WHERE pid=:rid"
" AND coalesce((SELECT value FROM tagxref"
" WHERE tagid=%d AND rid=:rid),'trunk')"
" == coalesce((SELECT value FROM tagxref"
" WHERE tagid=%d AND rid=plink.cid),'trunk');",
TAG_BRANCH, TAG_BRANCH
);
db_bind_int(&checkIfLeaf, ":rid", rid);
|
| ︙ | ︙ |
Changes to src/name.c.
| ︙ | ︙ | |||
199 200 201 202 203 204 205 |
}else if( fossil_strcmp(zTag, "prev")==0
|| fossil_strcmp(zTag, "previous")==0 ){
zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid="
"(SELECT pid FROM plink WHERE cid=%d AND isprim)",
vid);
}else if( fossil_strcmp(zTag, "next")==0 ){
zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid="
| | | | 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 |
}else if( fossil_strcmp(zTag, "prev")==0
|| fossil_strcmp(zTag, "previous")==0 ){
zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid="
"(SELECT pid FROM plink WHERE cid=%d AND isprim)",
vid);
}else if( fossil_strcmp(zTag, "next")==0 ){
zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid="
"(SELECT cid FROM plink WHERE pid=%d"
" ORDER BY isprim DESC, mtime DESC)",
vid);
}
}
}
return zUuid;
}
|
| ︙ | ︙ |
Changes to src/timeline.c.
| ︙ | ︙ | |||
95 96 97 98 99 100 101 |
@ <a href="%s(g.zTop)/timeline?u=%T(zU)">%h(zU)</a>%s(zSuf)
}
}else{
@ %s(zU)
}
}
| < < < < < < < < < < < < < < < < < < < < < < | 95 96 97 98 99 100 101 102 103 104 105 106 107 108 |
@ <a href="%s(g.zTop)/timeline?u=%T(zU)">%h(zU)</a>%s(zSuf)
}
}else{
@ %s(zU)
}
}
/*
** Allowed flags for the tmFlags argument to www_print_timeline
*/
#if INTERFACE
#define TIMELINE_ARTID 0x0001 /* Show artifact IDs on non-check-in lines */
#define TIMELINE_LEAFONLY 0x0002 /* Show "Leaf", but not "Merge", "Fork" etc */
#define TIMELINE_BRIEF 0x0004 /* Combine adjacent elements of same object */
|
| ︙ | ︙ |
Changes to test/graph-test-1.wiki.
| ︙ | ︙ | |||
58 59 60 61 62 63 64 |
From e663bac6f7 to a298a0e2f9 by shortest path.</a>
* <a href="../../../timeline?from=e663bac6f7&to=a298a0e2f9&nomerge"
target="testwindow">
From e663bac6f7 to a298a0e2f9 without merge links.</a>
* <a href="../../../timeline?me=e663bac6f7&you=a298a0e2f9"
target="testwindow">
Common ancestor path of e663bac6f7 to a298a0e2f9.</a>
| | > > | 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 |
From e663bac6f7 to a298a0e2f9 by shortest path.</a>
* <a href="../../../timeline?from=e663bac6f7&to=a298a0e2f9&nomerge"
target="testwindow">
From e663bac6f7 to a298a0e2f9 without merge links.</a>
* <a href="../../../timeline?me=e663bac6f7&you=a298a0e2f9"
target="testwindow">
Common ancestor path of e663bac6f7 to a298a0e2f9.</a>
* <a href="../../../timeline?f=65dd90fb95a2af55">
Merge on the same branch does not result in a leaf.
</a>
External:
* <a href="http://www.sqlite.org/src/timeline?c=2010-09-29&nd"
target="testwindow">Timewarp due to a mis-configured system clock.</a>
|