FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

Mango Beta 9
Goto page Previous  1, 2, 3, 4, 5  Next
 
Post new topic   Reply to topic     Forum Index -> Mango
View previous topic :: View next topic  
Author Message
JJR



Joined: 22 Feb 2004
Posts: 1104

PostPosted: Sat Jul 10, 2004 2:54 pm    Post subject: Reply with quote

kris wrote:
kris wrote:
... a bunch of multicasting stuff that hasn't yet been tested on linux so, while I'm disappointed, I'm not too wildly surprised

May have located the segfault by accident ~ will post again tomorrow, and place a beta_9a.zip on SVN


Hey Kris,

After running across a post on the newsgroup, I realized that gdb could have some usefulness. Running mangotest within gdb produced the location of the segfault (I feel stupid for not trying this before):

0x0804eea7 in _D5mango2io6Buffer6Buffer5writeFDFAvZiZi ()

There appears to be a problem with a call to the write member in mang/io/Buffer.d.

Unfortunately, I'm having difficulty tracking down the location in unittest.d that makes this call... somewhere in testInvalidatee? I'll try adding some breakpoints. Command line gdb seems to be the only debugger that is actually useful for d on linux.

Was this the problem you fixed in the new beta?

(useing dmd 0.95)

Later,

John
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 3:14 pm    Post subject: Reply with quote

If you can, would you mind running testClassSerialization()? If that works then try testMulticast(), which requires a couple of CR hits to display anything.

Thanks much;
Back to top
View user's profile Send private message
JJR



Joined: 22 Feb 2004
Posts: 1104

PostPosted: Sat Jul 10, 2004 3:28 pm    Post subject: Reply with quote

Yep no problem. Here are the results:

--- testClassSerialization() seemed to work. Output:

1090921693184 INFO mango.unittest - Done

(Now recompiling unittest/mango with testMulticast)

--- testMultcast() segfaulted. Output after 2 carriage returns:

listener received 1000 bytes

1090921695736 INFO mango.unittest - Done
Segmentation fault

--- Running the last test through gdb gave this result:

Program received signal SIGSEGV, Segmentation fault.
0x0806abad in _D3gcx3Gcx4markFPvPvZv()

I don't know what "mark" is... Are we getting any closer?

later,

John
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 3:46 pm    Post subject: Reply with quote

The logger output is amusing; look at those huge time stamps! Something to fix there Shocked

I'm guessing it's mango.io.SocketListener that's segfaulting. Can you insert a few juicy printf() into select locations within the run() method? For example:
Code:

        override int run()
        {
printf (" listener enter\n");
                while (true)
                       try {
                           // wait for incoming content
                           reader.read (buffer);
printf ("listener read() complete\n");

                           // time to quit?
                           if (quit || Socket.isCancelled())
                               break;
                           
printf ("listener pre-notify\n");
                           // invoke callback                       
                           notify (buffer);
printf ("listener post-notify\n");

                           } catch (Object x)
                                   {
printf ("listener exception\n");
                                   // time to quit?
                                   if (quit || Socket.isCancelled())
                                       break;
                           
                                   printf ("SocketListener: ?.*s\n", x.toString());
                                   //Stderr.put ("Exception: "~x.toString).cr();
                                   }
printf ("listener exit\n");
                return 0;
        }
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 3:56 pm    Post subject: Reply with quote

kris wrote:
The logger output is amusing; look at those huge time stamps! Something to fix there Shocked


Fixed that one!
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 3:59 pm    Post subject: Reply with quote

JJR wrote:
0x0806abad in _D3gcx3Gcx4markFPvPvZv()

gdb is not so smart: heck ~ even the execution address say's there was "a bad" in the noted function ...
Back to top
View user's profile Send private message
JJR



Joined: 22 Feb 2004
Posts: 1104

PostPosted: Sat Jul 10, 2004 4:03 pm    Post subject: Reply with quote

kris wrote:
JJR wrote:
0x0806abad in _D3gcx3Gcx4markFPvPvZv()

gdb is not so smart: heck ~ even the execution address say's there was "a bad" in the noted function ...


LOL! Laughing
Back to top
View user's profile Send private message
JJR



Joined: 22 Feb 2004
Posts: 1104

PostPosted: Sat Jul 10, 2004 4:10 pm    Post subject: Reply with quote

kris wrote:
The logger output is amusing; look at those huge time stamps! Something to fix there Shocked

I'm guessing it's mango.io.SocketListener that's segfaulting. Can you insert a few juicy printf() into select locations within the run() method.


Ok... I've done so. It appears the catch{} exception path is not taken... The problem lies elsewhere, I guess. Here's the progression:

listener read() complete
listener pre-notify
listner received 1000 bytes
listener post-notify

1090921697497 INFO mango.unittest - Done
Segmentation fault

My question is: why did "listener exit" not get printed?
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 4:33 pm    Post subject: Reply with quote

hmmmm ... I was guessing at SocketListener since the exception happens after the main() thread says it's "done". A segfault happening after that is typically in a different thread which, in this case, is the SocketListener thread. You probably don't see "listener exit" because it segfaults before that point is reached, and before an exception is thrown within that thread.

The problem here is that the listener thread is blocked by the OS, waiting for some content to arrive on the socket. The only way to interrupt that is to ... interrupt it, which happens when the program exits. That's why there's those funky checks for 'quit' and so on within the catch{} block (we expect an exception here when the program exits and that socket-read is forceably terminated).

I'm wondering how to isolate this further. You might add a
Code:
        byte x;
        Stdin >> x;

right before the return 0; of main(). At least that would further isolate the issue to the SocketListener() thread (a little pause can sometimes help).

You might also add a printf to the static destructor in mango.io.Socket, to see if and when that get's invoked. It's near the top of the file

Code:
static ~this()
{
printf ("static destructor\n");
        Socket.cancelAll (true);
        version(Win32)
        {
                WSACleanup();
        }
}


Another thing to try would be to add some printf() stuff within mango.io.DatagramSocket to see what the receive() method is returning:

Code:
        int read (IBuffer target)
        in {
           assert (target);
           }
        body
        {
                int reader (void[] src)
                {
                        int count = receive (src);

printf ("receive() ?d bytes\n", count);

                        if (count <= 0)
                            count = IConduit.Eof;
                        return count;
                }

                return target.write (&reader);
        }
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 5:06 pm    Post subject: Reply with quote

Another possibility is something barfing within a destructor ... I'll think about that one for a bit.

(BTW; all this stuff works perfectly under Win32 ~ including a variety of boundary conditions. We just have to unearth the linux gotcha's).
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 5:42 pm    Post subject: Reply with quote

Here a snapshot of the Win32 output for testMulticast()

listener received 1000 bytes

2015 INFO mango.unittest - Done
Socket static destructor
SocketListener: Failed while receiving socket data. Error # 10004
SocketListener: Failed while receiving socket data. Error # 10093
SocketListener: Failed while receiving socket data. Error # 10093
InBuffer destructor 'in'
InBuffer destructor 'out'
SocketListener destructor


I commented out the catch-block "we're quitting" test within SocketListener.run(), so you can see what's expected of that thread when the program exits (it throws a few exceptions).

I also added some destructor traces. Here's one (in unittest):
Code:

void testMulticast()
{
        class InBuffer : Buffer
        {
                char [] name;

                this (int size, char[] name)
                {
                        super (size);
                        this.name = name;
                }

                this (void[] x, int size, char[] name)
                {
                        super (x, size);
                        this.name = name;
                }

                ~this ()
                {
                        printf ("InBuffer destructor '?.*s'\n", name);
                }
        }

        MulticastSocket ms = new MulticastSocket ();
        InternetAddress ia = new InternetAddress ("226.1.1.1", 4444);

        byte[1000] xx;
        Buffer b = new InBuffer (xx, xx.length, "out");

        void listen (IBuffer buffer)
        {
                printf ("listener received ?d bytes\n", buffer.readable());
        }

        ms.join (ia);
        ISocketListener s = new SocketListener (ms, new InBuffer(1500, "in"), &listen);

        byte x;
        Stdin >> x;
        ms.write (b, ia);

        Stdin >> x;
}


and here's the other (in SocketListener):

Code:
        ~this()
        {
                printf ("SocketListener destructor\n");
        }

        override int run()
        {
                while (true)
                       try {
                           // wait for incoming content
                           reader.read (buffer);

                           // time to quit?
                           if (quit || Socket.isCancelled())
                               break;
                           
                           // invoke callback                       
                           notify (buffer);
                           } catch (Object x)
                                   {
                                   // time to quit?
                                   //if (quit || Socket.isCancelled())
                                      // break;
                           
                                   printf ("SocketListener: ?.*s\n", x.toString());
                                   }
                return 0;
        }
Back to top
View user's profile Send private message
JJR



Joined: 22 Feb 2004
Posts: 1104

PostPosted: Sat Jul 10, 2004 6:26 pm    Post subject: Reply with quote

With the changes, none of the destructors except ~Socket seem to get called. The program halts after printing out (as before):

listener received 1000 bytes

<big time #> INFO mango.unittest - Done
Socket.d: static destructor
Segmentation fault

Doesn't get further than this....

By the way, thanks for explaining about the thread ending after main... makes sense now.
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 6:44 pm    Post subject: Reply with quote

How about removing the Socket.d static destructor altogether? I wonder if there's a problem making a method call and/or assignment within a static destructor on linux?

Another thing to try would be to indicate, in testMulticast(), to the SocketListener that it should quit after just one good read (via method s.cancel):
Code:
        ms.join (ia);
        ISocketListener s = new SocketListener (ms, new Buffer(1500), &listen);

        s.cancel();

        byte x;
        Stdin >> x;
        ms.write (b, ia);

        Stdin >> x;

I'm hoping that will execute cleanly. Note that the notify() callback will not happen anymore, since it doesn't get called if 'quit' is flagged. If this works as expected, you might move the notify() call above the "quit" test in SocketListener.run() to see if it's the callback that screws things up ...
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 6:50 pm    Post subject: Reply with quote

JJR wrote:
<big time #> INFO mango.unittest - Done

If you wanna' patch that huge timestamp before the next Beta, you could change mango.log.Event to have this inside the version(linux) section of the static constructor (should be around line 157):
Code:
beginTime = (cast(ulong) tv.tv_sec) * 1000 + tv.tv_usec / 1000;

I had forgotten to put in the cast(ulong), so the expression was overflowing.

- Kris
Back to top
View user's profile Send private message
kris



Joined: 27 Mar 2004
Posts: 1494
Location: South Pacific

PostPosted: Sat Jul 10, 2004 7:11 pm    Post subject: Reply with quote

One of the nice things about CA is the number of reasonably good open-air concert theaters. Today the weather is far too nice to be coding and debugging, so I'm away to try and get very-last-minute tickets for Rush (gig starts in 1.5 hours) at my favourite open-air venue: Concord Pavillion.

Will check in later tonight.
Back to top
View user's profile Send private message
Display posts from previous:   
Post new topic   Reply to topic     Forum Index -> Mango All times are GMT - 6 Hours
Goto page Previous  1, 2, 3, 4, 5  Next
Page 3 of 5

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group