[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

Re: gEDA-user: pcb: a segfault bug in rats.c:AddAllRats()



On Tue, 2007-03-06 at 09:53 +0000, Seb James wrote:
> On Mon, 2007-03-05 at 17:06 +0000, Seb James wrote:
> > Quite possibly not the list to put this message. I'll put this in bug
> > tracking as well.
> > 
> > Here is a crashing bug with pcb:
> > 
> > This occurs when I disperse all the elements in my design. There are a
> > lot of them and they run off the page even if I set it to the max size
> > 30000 by 30000. The key thing is that the elements disperse off the
> > diagram.
> > 
> > Once dispersed off the edge of the diagram, if I call the optimize rats
> > nest function, I get a segfault:
> 
> With more testing, and setting the size of the diagram to allow me to
> disperse all the elements, I find that the crashing still occurs when I
> load the netlist, then "disperse all elements", then try to "optimize
> the rats nest".
> 
> If I _don't_ disperse, but manually move a few components out into the
> diagram, then the "optimize rats nest" step completes with no crash.

The bug was triggered by the following problem in my design:

Can't find U3551 pin 99 called for in netlist.
Can't find U3551 pin 87 called for in netlist.
Can't find U3551 pin 75 called for in netlist.
Can't find U3551 pin 63 called for in netlist.

etc etc (lots more messages)...

The crash occurred in rats.c, around line 610 in the function
DrawShortestRats() where CreateNewRat() is called with some arguments
which don't exist. There was no check in DrawShortestRats() that these
arguments are safe to pass to CreateNewRat() so I have patched the file;
patch attached.

This patch has been generated comparing with pcb 20070208.

Now I have to find out why these pins aren't in the netlist...

Seb
--- rats.c.orig	2007-02-04 02:29:28.000000000 +0000
+++ rats.c	2007-03-06 13:25:25.000000000 +0000
@@ -342,6 +342,7 @@
 {
   ConnectionTypePtr conn;
 
+  /* It would be worth checking if SourceNet is NULL here to avoid a segfault. Seb James. */
   CONNECTION_LOOP (SourceNet);
   {
     conn = GetConnectionMemory (DestNet);
@@ -575,11 +576,13 @@
   register float distance, temp;
   register ConnectionTypePtr conn1, conn2, firstpoint, secondpoint;
   Boolean changed = False;
+  Boolean havepoints = False;
   Cardinal n, m, j;
   NetTypePtr next, subnet, theSubnet = NULL;
 
+  if (Netl->NetN < 2) { return False; }
   firstpoint = secondpoint = NULL;
-  while (Netl->NetN > 1)
+  do
     {
       subnet = &Netl->Net[0];
       distance = SQUARE (MAX_COORD);
@@ -598,34 +601,38 @@
 		      distance = temp;
 		      firstpoint = conn1;
 		      secondpoint = conn2;
+		      havepoints = True;
 		      theSubnet = next;
 		    }
 		}
 	    }
 	}
-      if (funcp)
-	{
-	  (*funcp) (firstpoint, secondpoint, subnet->Style);
-	}
-      else
-	{
-	  /* found the shortest distance subnet, draw the rat */
-	  if ((line = CreateNewRat (PCB->Data,
-				    firstpoint->X, firstpoint->Y,
-				    secondpoint->X, secondpoint->Y,
-				    firstpoint->group, secondpoint->group,
-				    Settings.RatThickness,
-				    NoFlags ())) != NULL)
-	    {
-	      AddObjectToCreateUndoList (RATLINE_TYPE, line, line, line);
-	      DrawRat (line, 0);
-	      changed = True;
-	    }
-	}
+      if (havepoints == True)
+        {
+        if (funcp)
+	  {
+	    (*funcp) (firstpoint, secondpoint, subnet->Style);
+	  }
+        else
+	  {
+	    /* found the shortest distance subnet, draw the rat */
+	    if ((line = CreateNewRat (PCB->Data,
+				      firstpoint->X, firstpoint->Y,
+				      secondpoint->X, secondpoint->Y,
+				      firstpoint->group, secondpoint->group,
+				      Settings.RatThickness,
+				      NoFlags ())) != NULL)
+	      {
+	        AddObjectToCreateUndoList (RATLINE_TYPE, line, line, line);
+	        DrawRat (line, 0);
+	        changed = True;
+	      }
+	  }
 
-      /* copy theSubnet into the current subnet */
-      TransferNet (Netl, theSubnet, subnet);
-    }
+        /* copy theSubnet into the current subnet */
+        TransferNet (Netl, theSubnet, subnet);
+      } /* if (havepoints == True) */
+    } while (Netl->NetN > 1 && havepoints == True);
   /* presently nothing to do with the new subnet */
   /* so we throw it away and free the space */
   FreeNetMemory (&Netl->Net[--(Netl->NetN)]);

_______________________________________________
geda-user mailing list
geda-user@xxxxxxxxxxxxxx
http://www.seul.org/cgi-bin/mailman/listinfo/geda-user