Tsocket

Tsocket

Postby reinaldocrespo » Tue Aug 29, 2006 5:25 pm

Hi,

For some reason when trying to create a socket connection to a given port on at a given IP, the socket gets created at the local computer's ip instead. Here is my code:
Code: Select all  Expand view
      oSocket := TSocket():New( 15000 )
      osocket:lDebug := .t.
      oSocket:cLogfile := cFilePath( GetModuleFileName( GetInstance() ) ) + "trace.log"
      oSocket:bRead    = { | oSocket | aadd( m->aAcks, oSocket:GetData() ) }
      oSocket:bConnect = { || logfile( "trace.log", { "Connected to ip:"+osocket:cIpAddr } ) }
      oSocket:Connect( "98.19.1.4" )


Here I'm trying to connec to a local server at ip 98.19.1.4 which is listening on port 15000. But when I look at the trace.log file I find it is connecting to ip 98.19.1.187 which is the local computer's ip and not to the desired ip, thus any send/receive data attemp fails.

Any Ideas why?

The funny thing is that yesterday it was connecting to the right ip and I got to send and receive data just perfectly. I know as a matter of fact that the server is listening at 15000 and that the server's ip is correct.

I'm using xharbour 0.99.61 w/FW2.7 + BCC 5.5.



Reinaldo.
User avatar
reinaldocrespo
 
Posts: 979
Joined: Thu Nov 17, 2005 5:49 pm
Location: Fort Lauderdale, FL

Postby James Bott » Tue Aug 29, 2006 5:35 pm

Hi Rienaldo,

I have not done much work with sockets, but I know that when strange things are happening that don't seem to make sense (with any code), sometimes adding a sysRefresh() fixes the problem. It's worth a try. I would put it just before the connect.

James
User avatar
James Bott
 
Posts: 4840
Joined: Fri Nov 18, 2005 4:52 pm
Location: San Diego, California, USA

Postby reinaldocrespo » Tue Aug 29, 2006 8:16 pm

James;

Thank you for your reply. I inserted sysfresh(). Still same behavior.

Listen, anyone can try this even without a socket server working listening. If you try to connect to non existent IP it connects to your own ip even if no service is listening on the specified port.

Try using my very same example above. You'll get connection or so is tsocket's behavior although no real connection exists.

Reinaldo
User avatar
reinaldocrespo
 
Posts: 979
Joined: Thu Nov 17, 2005 5:49 pm
Location: Fort Lauderdale, FL

Postby James Bott » Tue Aug 29, 2006 8:31 pm

Reinaldo,

I tried running it here and it hung at this line:

oSocket:bRead ...

I commented out that line and it runs through all the rest of the lines but I get no trace.log so it seems I am NOT getting a connection. I also disabled my firewall but there was no change.

James
User avatar
James Bott
 
Posts: 4840
Joined: Fri Nov 18, 2005 4:52 pm
Location: San Diego, California, USA

Postby reinaldocrespo » Tue Aug 29, 2006 8:41 pm

James;

Check again. Sometimes it takes a few seconds for the trace.log file to create and have info on it.

I'm testing it here on my own computer where I have no access to private ip 98.19.1.4, and I do get a trace file. It reads : Connected to ip:192.168.1.2.

The line osocket:bRead := ... is just assigning a code block to a variable. I wonder why would it hang....? Makes no sense to me.

Check again your app directory for trace.log.
User avatar
reinaldocrespo
 
Posts: 979
Joined: Thu Nov 17, 2005 5:49 pm
Location: Fort Lauderdale, FL

Postby reinaldocrespo » Tue Aug 29, 2006 9:19 pm

Here is a self contained sample:
compile and execute. After 30 seconds check your app's dir. You'll find a trace.log file and an actual connection where you can click on send and no error is reported. Futhermore, Tsocket reports being connected to your local computer's ip instead of the assigned ip.

Unless I'm missing something here, this self contained sample proves how tsocket is not working properly???

Code: Select all  Expand view
#include "Fivewin.ch"

FUNCTION MAIN()
LOCAL oWnd
local oMsg

   DEFINE WINDOW oWnd

   @ 1, 2 BUTTON "Send";
      SIZE 100, 50;
      ACTION ( oMsg:CreateHL7Message(), ;
                 oMsg:Tcp_HL7_Transmit(), ;
            omsg:IsAcknowledged() )

   ACTIVATE WINDOW oWnd ;
          ON INIT ( oMsg := tExporter():new(), omsg:SetupIPSocket() ) ;
      VALID( omsg:end(), .t. )

RETURN NIL

*-------------------------------------------------------------------------------------------------------------------------------
CLASS TEXPORTER

   DATA oSocket
   DATA isConnected AS LOGIC INIT .f.
   DATA nPort AS NUMERIC INIT 15000
   DATA cIp, cId, cHL7
   DATA aAcks AS ARRAY INIT {}

   METHOD New() CONSTRUCTOR
   METHOD SetupIpSocket()
   METHOD Tcp_Hl7_Transmit()
   METHOD isAcknowledged()
   METHOD CreateHL7Message()

   METHOD UniqueId()      // HL7 segments
   METHOD obx()
   METHOD obr()
   METHOD orc()
   METHOD Pid()
   METHOD Env()
   METHOD Msh()
   METHOD nte()

   METHOD End()

END CLASS

*-------------------------------------------------------------------------------------------------------------------------------
METHOD new() CLASS TEXPORTER

   ::nPort := 15000
   ::cIP := "98.19.1.4"

RETURN SELF

*-------------------------------------------------------------------------------------------------------------------------------
METHOD SetupIpSocket() CLASS TEXPORTER

   ::oSocket := TSocket():New( ::nport )
   ::osocket:lDebug := .t.
   ::oSocket:cLogfile := cFilePath( GetModuleFileName( GetInstance() ) ) + "trace.log"
   ::oSocket:bRead    = { | oSocket | aadd( ::aAcks, oSocket:GetData() ) }
   ::oSocket:bConnect = { || ::isConnected := .t., logfile( "trace.log", { "Connected to ip:", ::osocket:cIpAddr } ) }
   ::oSocket:Connect( ::cIp )

RETURN NIL


RETURN NIL

*-------------------------------------------------------------------------------------------------------------------------------
METHOD CreateHL7Message() CLASS TEXPORTER

   ::uniqueId()
   ::cHL7 := chr( 11 ) + ::msh() + chr(13) + ;
      ::env() + chr( 13 ) + ;
      ::pid() + chr( 13 ) + ;
      ::orc() + chr( 13 ) + ;
      ::obr() + chr( 13 ) + ;
      ::obx() + chr( 13 ) + ;
      /*::nte() + chr( 13 ) +*/ chr( 28 ) + chr( 13 )

RETURN NIL

*-------------------------------------------------------------------------------------------------------------------------------
METHOD Tcp_HL7_Transmit() CLASS TEXPORTER

   if !::isConnected
      MsgStop( "Connection to " + ::oSocket:cIpAddr + " at " + cValToChar( ::osocket:nPort ) + " failed." )
      Return Nil
   Endif

   ::oSocket:SendData( ::cHL7 )

RETURN NIL

*-------------------------------------------------------------------------------------------------------------------------------
METHOD isAcknowledged() CLASS TEXPORTER
local aParsed
local nPos

   if !empty( ::aAcks )
      aParsed    := HB_ATOKENS( aTail( ::aAcks ), chr( 13 ), .T., .F.)
      nPos       := aScan( aParsed, { |e| left( e, 3 ) == "MSA" } )

      if nPos > 0
         aParsed := HB_ATOKENS( aParsed[ nPos ], "|", .T., .F. )
         if alltrim( aParsed[ 3 ] ) == alltrim( ::cId ) .and. "NORMAL" $ upper( aParsed[ 4 ] )
            RETURN .T.
         Endif
      endif
   Endif

RETURN .F.

*-------------------------------------------------------------------------------------------------------------------------------
METHOD Msh() CLASS TEXPORTER
local cStr := "MSH|"

   cStr += "^~\&|"         //2- encoding chars
   cStr += "MP8-PathLabs|"      //3- snd app
   cStr += "|"            //4- snd facility
   cStr += "|"            //5- recv app
   cStr += "|"            //6- recv facility
   cstr += DTOS( date() ) + StrTran( time(), ":", "" )+ "|" //7
   cStr += "|"            //8
   cstr += "ORU^R01|"      //9
   cstr += ::cId + "|"      //10
   cStr += "||||"

RETURN cStr

*-------------------------------------------------------------------------------------------------------------------------------
METHOD Env( cTrigger ) CLASS TEXPORTER
local cStr := "EVN|"

   cStr += "R01|"
   cStr += DTOS( date() ) + StrTran( time(), ":", "" ) + "|"

RETURN cStr

*-------------------------------------------------------------------------------------------------------------------------------
METHOD Pid() CLASS TEXPORTER
local cStr := "PID|"

   cStr += "||"
   cStr += "REC:00000001|"
   cStr += "||||||||||||||"
   cStr += "ACC:00000001^^^^^|"
   cStr += "|"

RETURN cStr

*-------------------------------------------------------------------------------------------------------------------------------
METHOD orc() CLASS TEXPORTER
local cStr := "ORC|"

   cStr += "RE|"
   cStr += "ORDER:0000000^|"
   cStr += "|||||||"
   cStr += "USERID|"
   cStr += "|||||||||"

RETURN cStr

*-------------------------------------------------------------------------------------------------------------------------------
METHOD obr() CLASS TEXPORTER
local cStr := "OBR|"

   cStr += "ORDER:0000001^|"
   cStr += "|||||"
   cStr += DTOS( Date() ) + StrTran( Time(), ":", "" ) + "|"
   cStr += "||"
   cStr += "TRNSCRIPT|"
   cStr += "||||||||||||||"
   cStr += "F|"
   cStr += "||||||"
   cStr += "PTHLGST^PthlgstNameString|"
   cStr += "|||||||||||"

RETURN cStr

*-------------------------------------------------------------------------------------------------------------------------------
METHOD obx() CLASS TEXPORTER
local cStr   := ""
local nSeq
//local aRsts   :={ ::oTrans:oTrGrss:GetText(), ::oTrans:oTrDg:GetText() }
local aRsts   := { "Text line one.  Sample text.  The fox jumped over the white fence", ;
            "Text line two.  Sample text. More foxes jumped over the white fence" }

   For nSeq := 1 to 2
      cStr    += "OBX|"
      cStr += cValToChar( nSeq )+ "|"
      cStr += "ST|"
      cStr += "||"
      cStr += aRsts[ nSeq ] +"|"
      cStr += "||||||||||||" + chr(13)
   Next nSeq

RETURN cStr

*-------------------------------------------------------------------------------------------------------------------------------
METHOD Nte() CLASS TEXPORTER
local cStr   := "NTE|"

RETURN cStr

*-------------------------------------------------------------------------------------------------------------------------------
METHOD UniqueId() CLASS TEXPORTER
local cPrvId := ::cId

   While ::cId == cPrvId
      ::cid := Right( cValToChar( Year(date() ) ), 2 ) + ;
           StrZero( Month( date() ),2 ) + ;
           StrZero( Day( date() ),2 ) + ;
           cValToChar( Seconds() )
   End

return nil

*-------------------------------------------------------------------------------------------------------------------------------
METHOD End() CLASS TEXPORTER

   iif( upper( valtype( ::osocket ) ) == "O", ::osocket:End(), )

RETURN NIL
User avatar
reinaldocrespo
 
Posts: 979
Joined: Thu Nov 17, 2005 5:49 pm
Location: Fort Lauderdale, FL

reinaldo a good ip monitor give us a gread hand.

Postby eduardofreni » Tue Aug 29, 2006 10:06 pm

I worked with socket.
My FiveWin WebServer, have 4 years of work and give me 0 problems. All maked with fivewin class with few modify.
I am satisfied from this tecnology in Fivewin.
But prior of write a software for network, you have installed a network monitor?.
Else, in some case, you not succeed to find the problem, and you do not succeed to see how the net works.
Even if studies 100 books of tcpip, not are nothing better than an IP monitor.
You may be to see the network trafic in and out of your computer, the dialog with the server ecc ecc.

I try the ip monitor at http://www.networkactiv.com/
I use it from 3 year.
Test it you can resolve many problem.

Best Regards

Eduardo Freni
User avatar
eduardofreni
 
Posts: 12
Joined: Sat Aug 26, 2006 12:27 am
Location: Florence (Italy)

Postby reinaldocrespo » Wed Aug 30, 2006 12:12 am

Eduardo;

Thank you. I will try it.

Reinaldo.
User avatar
reinaldocrespo
 
Posts: 979
Joined: Thu Nov 17, 2005 5:49 pm
Location: Fort Lauderdale, FL

Postby James Bott » Wed Aug 30, 2006 1:10 am

Reinaldo,

OK, I guess I just didn't wait 30 seconds. I tried again and waited longer (my original code). I found the trace.log and I also looked at my firewall log. Here are the results:

Trace Log
08/29/06 17:59:22: Connect Socket handle: 1892
08/29/06 17:59:22: Connected to ip:192.168.0.101

---------------
Symantec Personal Firewall log
Connection: 192.168.0.102: 4095.
to MATRIX(192.168.0.101): netbios-ssn(139).
4 bytes sent.
660 bytes received.
3.144 elapsed time.

It seems that the firewall claims my computer "Matrix IP address 192.168.0.101) connected to itself, however, the firewall log says it created a new address 192.168.0.102. I don't know if this info is of any help.

James
User avatar
James Bott
 
Posts: 4840
Joined: Fri Nov 18, 2005 4:52 pm
Location: San Diego, California, USA

Postby reinaldocrespo » Wed Aug 30, 2006 1:45 am

James;

Thank you for the reply.

Regarding sockets, there seems to be more than what meets the eye or the obvious. Indeed you do have a socket connection. Although no real communication will ever occur, the socket client is up and "working".

I've had to just disregard, for now, certainty of a true connection to a listening port and proceed by faith with data sends and expect replys. If no acknoledgement is received with the expected acceptance message, then simply display an error message to alert the user. Interestingly enough I do get the expected answers from 98.19.1.4 although Tsocket:cipAddr contains the ip of the client computer where my app is running instead of the expected 98.19.1.4.

Perhaps I'm the last to find out that the notion of sockets is a very interesting subject at the very least. Think of the capabilities. You can actually have instruments (hardware) and different pieces of software speaking to each other. You could have a tsocket server listening on your client's server for messages from your own software to perform... the possibilities are endless. AMOF, no more RS232.

At this very moment I'm uploading pathological transcriptions results up to a main frame where doctors can connect to and view clinical histories of patients. At this moment I'm not totally happy with the way it is working for the reasons I explained above. But it is working nevertheless.


Reinaldo.
User avatar
reinaldocrespo
 
Posts: 979
Joined: Thu Nov 17, 2005 5:49 pm
Location: Fort Lauderdale, FL

Sockets

Postby AlexSchaft » Wed Aug 30, 2006 3:45 am

Hi,

One thing I found is that when the connection doesn't connect, the connect event still fires, but oSocket:ClientIP() returns "0.0.0.0"

oSocket:cIPAddr is always your own address, as set by

::cIPAddr = GetHostByName( GetHostName() )

in the new method.

HTH's

Alex
User avatar
AlexSchaft
 
Posts: 172
Joined: Fri Oct 07, 2005 1:29 pm
Location: Edenvale, Gauteng, South Africa


Return to FiveWin for Harbour/xHarbour

Who is online

Users browsing this forum: No registered users and 89 guests