🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: borland.public.cppbuilder.internet.socket
Article #1243

Re: Passing info between threads

#1243
From: Bob Gonder
Date: Fri, 23 Feb 2007 04:31
118 lines
5266 bytes
"Lesley Anne"  wrote:
>"Paul at NCF"  wrote in message 
>>
>> The thread could then get signaled and woken up, and remove the item off 
>> the queue.
>
>Yes.  That's what the HandleCommand is there for, and why it's in the 
>sctpThread.

Yes, it is a part of the Thread Class, but it is being called by the
VCL Thread. It is being executed by the VCL thread, not the sctp
thread.  The Thread::Execute() needs to be calling the HandleCommand
code when data becomes available to send.

>> Not sure it did.  Looked to me like the VCL thread added the command to 
>> the queue, and then calls the threads handle command to take it off the 
>> queue and process it?
>
>Isn't that what you just said it should do?

No, it should _signal_ the thread to send the data, not _call_ the
thread function that does the actual work.

>> WaitForMultipleObjects would only wake up the thread when something was 
>> signalled.  And it would only block the VCL thread when it was locked
>
>But I can't have the thread sleeping or waiting or anything else that would 
>keep it from processing the library's event loop.

Why do you have an event loop? I thought you were using blocking
calls.

>  It might be a while 
>before the next time the main unit initiates an outgoing message, but in the 
>meantime, the library still needs to keep looking for incoming messages.  It 
>relies on sctp_eventLoop() being called continuously.  Whatever I add into 
>the Execute's while loop has to co-exist peacefully with:

void __fastcall TForm1::Send(String Message, int Site)
{
   if (sctpThread) {
      TSctpCmdParams *SctpCmdParams = new TSctpCmdParams;

             SctpCmdParams->Command   = scmdSend;
             SctpCmdParams->AssocID   = associationID[Site];
      strcpy(SctpCmdParams->MsgBuffer,  Message.c_str());
             SctpCmdParams->MsgLen    = Message.Length();

      SctpCommandList->Add(SctpCmdParams);

	evSendEvent->SetEvent( );	// <<<---

   } else
      Memo1->Lines->Add("ERROR: sctp Thread does not exist");
}


 ....... ....... TsctpThread::Execute( ..... )
{
	/* setup the thread and sending socket info */
	/* not shown */

>    while (! Terminated ) {

	// no delay or locks
	// acts like non-existant  if( evSendEvent->Signaled )
	if( evSendEvent->WaitFor( 0 ) == wrSignaled )
	{
		// Only Locks when Signaled
		TList* List = SctpCommandList->LockList();
		if(  List->Count > 0 )
		{
		      TSctpCmdParams *SctpCmdParams =
			 (TSctpCmdParams*)List->First();
		      List->Delete( 0 );
		      SctpCommandList->UnlockList();

		     HandleCommand( SctpCmdParams );
		     >  if (sctp_eventLoop() < 0)
		     >	       break ;
		// In case 2 events came in and we missed the first
		    evSendEvent->SetEvent( );
		    continue; // skip the sleep()
		}else{
		    // no command listed, probably got here
		    // from the above SetEvent();
		      SctpCommandList->UnlockList();
		};
	};
	> if (sctp_eventLoop() < 0)
	>       break ;
	// give up time slice so other threads can do something.
	// since we have nothing to do right now.
	Sleep( 0 );
>    }

	/* Socket and Thread cleanup */
	/* not shown */
}

>and not block that eventLoop from happening.

I'm not sure what sctp_eventLoop is supposed to do for you.
In my stuff, I have One thread for Sending, and a Second thread for
Receiving.

In the Send thread, I WaitForSingleObject( hSendEvent, 1000 )
Which wakes up every second and checks for termination.
Otherwise, it sits using no CPU.
When Send request comes in, it does a blocking send, and checks for
another request before resuming the Wait. The App puts up a request,
then Signal( hSendEvent )

On the Application side, I have the same setup, blocking for a Receive
event that the Receive Thread sends when data becomes available.

The Receive Thread is mostly blocked on the Receive().
The Send Thread is mostly blocked on the WaitForSingleObject()
Technical Details
Message-ID: <72lst2pt6auavtcotu5tehbbjskhgps56k@4ax.com>
Path: arc1-ca.pugleaf.net!g2news2.google.com!news4.google.com!border1.nntp.dca.giganews.com!nntp.giganews.com!newsfeed00.sul.t-online.de!newsfeed01.sul.t-online.de!t-online.de!newsgroups.borland.com!not-for-mail
References: <45d9e83a$1@newsgroups.borland.com> <h21mt21bg7maqp25d2lqkr9b1iet0eu3g6@4ax.com> <45db2486$1@newsgroups.borland.com> <vj8nt2llf7deda6ioqggci4rds885qcmne@4ax.com> <45dcc0cb@newsgroups.borland.com> <45dd557c$1@newsgroups.borland.com> <45ddf727@newsgroups.borland.com> <45de1d0f@newsgroups.borland.com> <45de262d$1@newsgroups.borland.com>

Show Full Headers
Complete Article Headers
X-Google-Thread: 11508e,234a9a04e64155b0
X-Google-Attributes: gid11508e,public
X-Google-Language: ENGLISH,ASCII-7-bit
From: Bob Gonder <notbg@notmindspring.invalid>
Newsgroups: borland.public.cppbuilder.internet.socket
Subject: Re: Passing info between threads
Date: Thu, 22 Feb 2007 20:31:42 -0800
Organization: MindSpring Enterprises, Inc.
Reply-To: notbg@notmindspring.invalid
Message-ID: <72lst2pt6auavtcotu5tehbbjskhgps56k@4ax.com>
References: <45d9e83a$1@newsgroups.borland.com> <h21mt21bg7maqp25d2lqkr9b1iet0eu3g6@4ax.com> <45db2486$1@newsgroups.borland.com> <vj8nt2llf7deda6ioqggci4rds885qcmne@4ax.com> <45dcc0cb@newsgroups.borland.com> <45dd557c$1@newsgroups.borland.com> <45ddf727@newsgroups.borland.com> <45de1d0f@newsgroups.borland.com> <45de262d$1@newsgroups.borland.com>
X-Newsreader: Forte Agent 1.93/32.576 English (American)
MIME-Version: 1.0
Content-Type: text/plain; charset=us-ascii
Content-Transfer-Encoding: 7bit
NNTP-Posting-Host: 71.0.35.190
X-Trace: newsgroups.borland.com 1172205057 71.0.35.190 (22 Feb 2007 20:30:57 -0800)
Lines: 121
Path: arc1-ca.pugleaf.net!g2news2.google.com!news4.google.com!border1.nntp.dca.giganews.com!nntp.giganews.com!newsfeed00.sul.t-online.de!newsfeed01.sul.t-online.de!t-online.de!newsgroups.borland.com!not-for-mail