On Thu, Nov 09, 2000 at 02:26:19PM +1100, Martin Sevior wrote:
> 
> 
> On Wed, 8 Nov 2000, Sam TH wrote:
> > 
> > Ha - I win.  The following patch fixes the problem for me.
> > As it turns out, the problem was much worse than it appeared.  Just
> > try opening a new document, and hitting the left arrow key.  Instant
> > segfault.  This fixes that, and the undo of fields at the beginning
> > of the document, and I think a bunch of other problems.  Detailed 
> > explanation after the patch.  
> > 
> 
> Glad I was starting on this then :-)
> 
> > Patch:
> > 
> > diff -u -r1.307 fv_View.cpp
> > --- src/text//fmt/xp/fv_View.cpp    2000/11/09 01:00:57     1.307
> > +++ src/text//fmt/xp/fv_View.cpp    2000/11/09 02:59:46
> > @@ -4567,6 +4567,9 @@
> >     UT_sint32 iPointHeight;
> >  
> >     fl_BlockLayout* pBlock = _findBlockAtPosition(pos);
> > +   while(!pBlock)
> > +           pBlock =  _findBlockAtPosition((PT_DocPosition) pos++);
> > +
> >     UT_ASSERT(pBlock);
> >     fp_Run* pRun = pBlock->findPointCoords(pos, bEOL, xPoint, yPoint, 
>iPointHeight);
> >  
> > Explanation:
> > 
> > The problem was, we were asking for the Block in the document at or before
> > pos.  However, if pos == 1, then there was no block that fit these 
> > criteria.  Then, when you try to use pBlock about at the bottom of the patch
> > there, it segfaults.  In order to fix this, I just said that if we don't 
> > find the block there, we keep going through the document until we find
> > one.  
> > 
> > This could have been done deeper in the call chain resulting from 
> > _findBlockAtPosition(), but this was where the syntax was easiest.  
> > 
> > As this isn't really the answer we want in the case that we have to
> > use the while loop, this may introduce bugs.  Therefore, I haven't
> > committed it yet. If people think that it's not a good idea, I'll 
> > hold off, but this issue has to be fixed before 0.7.12 goes out.  
> > 
> 
> Yes there is a potential problem if pos runs past the end of the document.
> You might want a call to m_pDoc->getbounds() before/in the loop to make
> sure pos is sane. You use the code like this
> 
> 
>       PT_DocPosition posBOD;
>       PT_DocPosition posEOD;
>       UT_Bool bRes;
> 
>       bRes = m_pDoc->getBounds(UT_FALSE, posBOD);
>       bRes = m_pDoc->getBounds(UT_TRUE, posEOD);
>       UT_ASSERT(bRes);
>       
> I'll leave the details for you... (handwave, handwave)

Handwaving accepted.  Here's the revised patch.  If anyone has
objections, please speak now, or else I'll commit this.  

Index: src/text/fmt/xp/fv_View.cpp
===================================================================
RCS file: /cvsroot/abi/src/text/fmt/xp/fv_View.cpp,v
retrieving revision 1.307
diff -u -r1.307 fv_View.cpp
--- src/text/fmt/xp/fv_View.cpp 2000/11/09 01:00:57     1.307
+++ src/text/fmt/xp/fv_View.cpp 2000/11/09 07:37:04
@@ -4566,7 +4566,23 @@
        UT_sint32 yPoint;
        UT_sint32 iPointHeight;
 
+       PT_DocPosition posEOD;
+       UT_Bool bRes;
+
+
+       // The idea of the following code is thus: we need the previous block in 
+       // the document.  But at the beginning of the document, sometimes there
+       // isn't a previous block.  So we get the next block in the document.  
+       // If we don't do this, we end up in big trouble, since we reference
+       // that block in about 8 lines.   Sam, 11.9.00
+
+       bRes = m_pDoc->getBounds(UT_TRUE, posEOD);
+       UT_ASSERT(bRes);
        fl_BlockLayout* pBlock = _findBlockAtPosition(pos);
+       while(!pBlock && (pos < posEOD))
+               pBlock =  _findBlockAtPosition((PT_DocPosition) pos++);
+       pos = (PT_DocPosition) pos; 
+
        UT_ASSERT(pBlock);
        fp_Run* pRun = pBlock->findPointCoords(pos, bEOL, xPoint, yPoint, 
iPointHeight);
 

           
        sam th               
        [EMAIL PROTECTED]
        http://www.abisource.com/~sam/
        GnuPG Key:  
        http://pgp5.ai.mit.edu:11371/pks/lookup?op=get&search=0xCABD33FC

PGP signature

Reply via email to