Fossil

Check-in [399d1ca0]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Fix a bug in timeline graph generation.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: 399d1ca0006bf2f51c353a807f5b139bbb676041
User & Date: drh 2010-02-08 16:58:37
References
2010-02-08
17:22 New ticket [e42448ed] "co --latest" not working anymore?. artifact: 7414994f user: bharder
Context
2010-02-08
18:08
Check the graph for resize events every second and rerender the graph if a resize has occurred. This fixes display problems on Safari and also keeps the graph consistent with resized browser windows. check-in: f51bd596 user: drh tags: trunk
16:58
Fix a bug in timeline graph generation. check-in: 399d1ca0 user: drh tags: trunk
16:40
Fix a bug in the graph display that causes an assertion fault if the timeline contains a node that has no parents. check-in: c5f3e87b user: drh tags: trunk
Changes
Hide Diffs Unified Diffs Ignore Whitespace Patch

Changes to src/graph.c.

150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
...
175
176
177
178
179
180
181

182
183
184
185
186
187
188
...
219
220
221
222
223
224
225

226
227
228
229
230
231
232
233
234
235
236
237
238
239
240





241
242
243
244
245
246
247
...
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
  p->pLast = pRow;
}

/*
** Return the index of a rail currently not in use for any row between
** top and bottom, inclusive.  
*/
static int findFreeRail(GraphContext *p, int top, int btm){
  u32 inUseMask = 0;
  GraphRow *pRow;
  int i;
  for(pRow=p->pFirst; pRow && pRow->idx<top; pRow=pRow->pNext){}
  while( pRow && pRow->idx<=btm ){
    inUseMask |= pRow->railInUse;
    pRow = pRow->pNext;
  }
................................................................................
*/
void graph_finish(GraphContext *p){
  GraphRow *pRow, *pDesc;
  Bag allRids;
  int i;
  int nRow;
  u32 mask;


  if( p==0 || p->pFirst==0 || p->nErr ) return;

  /* Initialize all rows */
  bag_init(&allRids);
  nRow = 0;
  for(pRow=p->pFirst; pRow; pRow=pRow->pNext){
................................................................................
    }
  }

  /* Assign rails to all rows that are still unassigned.
  ** The first primary child of a row goes on the same rail as
  ** that row.
  */

  for(pRow=p->pLast; pRow; pRow=pRow->pPrev){
    int parentRid;
    if( pRow->iRail>=0 ) continue;
    assert( pRow->nParent>0 );
    parentRid = pRow->aParent[0];
    assert( bag_find(&allRids, parentRid) );
    for(pDesc=pRow->pNext; pDesc && pDesc->rid!=parentRid; pDesc=pDesc->pNext){}
    assert( pDesc!=0 );
    if( pDesc->aiRaiser[pDesc->iRail]==0 && pDesc->zBranch==pRow->zBranch ){
      pRow->iRail = pDesc->iRail;
    }else{
      pRow->iRail = findFreeRail(p, 0, pDesc->idx);
    }
    pDesc->aiRaiser[pRow->iRail] = pRow->idx;
    mask = 1<<pRow->iRail;





    for(pDesc = pRow; ; pDesc=pDesc->pNext){
      assert( pDesc!=0 );
      pDesc->railInUse |= mask;
      if( pDesc->rid==parentRid ) break;
    }
  }

................................................................................
  for(pRow=p->pFirst; pRow; pRow=pRow->pNext){
    for(i=1; i<pRow->nParent; i++){
      int parentRid = pRow->aParent[i];
      for(pDesc=pRow->pNext; pDesc && pDesc->rid!=parentRid;
          pDesc=pDesc->pNext){}
      if( pDesc==0 ) continue;
      if( pDesc->mergeOut<0 ){
        pDesc->mergeOut = findFreeRail(p, pRow->idx, pDesc->idx);
        pDesc->mergeUpto = pRow->idx;
      }
      pRow->mergeIn |= 1<<pDesc->mergeOut;
    }
  }

  /*







|
<







 







>







 







>











|



>
>
>
>
>







 







|







150
151
152
153
154
155
156
157

158
159
160
161
162
163
164
...
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
...
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
...
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
  p->pLast = pRow;
}

/*
** Return the index of a rail currently not in use for any row between
** top and bottom, inclusive.  
*/
static int findFreeRail(GraphContext *p, int top, int btm, u32 inUseMask){

  GraphRow *pRow;
  int i;
  for(pRow=p->pFirst; pRow && pRow->idx<top; pRow=pRow->pNext){}
  while( pRow && pRow->idx<=btm ){
    inUseMask |= pRow->railInUse;
    pRow = pRow->pNext;
  }
................................................................................
*/
void graph_finish(GraphContext *p){
  GraphRow *pRow, *pDesc;
  Bag allRids;
  int i;
  int nRow;
  u32 mask;
  u32 inUse;

  if( p==0 || p->pFirst==0 || p->nErr ) return;

  /* Initialize all rows */
  bag_init(&allRids);
  nRow = 0;
  for(pRow=p->pFirst; pRow; pRow=pRow->pNext){
................................................................................
    }
  }

  /* Assign rails to all rows that are still unassigned.
  ** The first primary child of a row goes on the same rail as
  ** that row.
  */
  inUse = 0;
  for(pRow=p->pLast; pRow; pRow=pRow->pPrev){
    int parentRid;
    if( pRow->iRail>=0 ) continue;
    assert( pRow->nParent>0 );
    parentRid = pRow->aParent[0];
    assert( bag_find(&allRids, parentRid) );
    for(pDesc=pRow->pNext; pDesc && pDesc->rid!=parentRid; pDesc=pDesc->pNext){}
    assert( pDesc!=0 );
    if( pDesc->aiRaiser[pDesc->iRail]==0 && pDesc->zBranch==pRow->zBranch ){
      pRow->iRail = pDesc->iRail;
    }else{
      pRow->iRail = findFreeRail(p, 0, pDesc->idx, inUse);
    }
    pDesc->aiRaiser[pRow->iRail] = pRow->idx;
    mask = 1<<pRow->iRail;
    if( pRow->isLeaf ){
      inUse &= ~mask;
    }else{
      inUse |= mask;
    }
    for(pDesc = pRow; ; pDesc=pDesc->pNext){
      assert( pDesc!=0 );
      pDesc->railInUse |= mask;
      if( pDesc->rid==parentRid ) break;
    }
  }

................................................................................
  for(pRow=p->pFirst; pRow; pRow=pRow->pNext){
    for(i=1; i<pRow->nParent; i++){
      int parentRid = pRow->aParent[i];
      for(pDesc=pRow->pNext; pDesc && pDesc->rid!=parentRid;
          pDesc=pDesc->pNext){}
      if( pDesc==0 ) continue;
      if( pDesc->mergeOut<0 ){
        pDesc->mergeOut = findFreeRail(p, pRow->idx, pDesc->idx, 0);
        pDesc->mergeUpto = pRow->idx;
      }
      pRow->mergeIn |= 1<<pDesc->mergeOut;
    }
  }

  /*