Omzetten vb6 socket code naar C#

Pagina: 1
Acties:

Onderwerpen


Acties:
  • 0 Henk 'm!

  • huub8
  • Registratie: Maart 2009
  • Laatst online: 28-06-2021
Voor een project heb ik een linksys router aangepast zodat deze signalen aan een microcontroller door geeft (een 8 bits signaal/nummer). Deze signalen/commando's krijgt hij op het moment nog van een in visual basic 6 geschreven programma dat draait op een draadloos met de router verbonden computer. Echter zou ik graag de xbox 360 controller gebruiken als input, en dit lukt mij niet onder vb6. Daarom zou ik graag de code omzetten naar C#, en hier gaat het fout.

De ertoe doende visual basic 6 code:

code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
Private Sub Command1_Click()
  If sock.State = sckClosed Then ' if the socket is closed
    sock.RemoteHost = lbladdress.Text ' set server adress
    sock.RemotePort = "1500" ' set server port
    Label5.Caption = "Connected"
    sock.Connect ' start connection attempt
  Else ' if the socket is open
    sock.Close ' close it
    Label5.Caption = "Not Connected"
  End If
End Sub


Sub motion(ttime As Integer)
    address = Form1.address
    output = ttime

    Rem vbOut address, output
    'sock.SendData output & Chr(0)
    If sock.State = sckConnected Then
     sock.SendData Chr(output + 1) & Chr(0)
      Label5.Caption = Chr(output + 1) & Chr(0)
    Else
        Label5.Caption = "Not sending data"
    End If
End Sub

Toelichting: ttime is hier dus het getal dat moet worden gestuurd, wat in de c# command heet.


Mijn poging de code om te zetten (aan de hand van code die ik op het internet vond):

code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
        private void cmdConnect_Click(object sender, System.EventArgs e)
        {
                //create a new client socket ...
                m_socWorker = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.IP);
                String szIPSelected  = txtIPAddress.Text;
                String szPort = txtPort.Text;
                int  alPort = System.Convert.ToInt16 (szPort,10);
            
                System.Net.IPAddress    remoteIPAddress  = System.Net.IPAddress.Parse(szIPSelected);
                System.Net.IPEndPoint   remoteEndPoint = new System.Net.IPEndPoint(remoteIPAddress, alPort);
                m_socWorker.Connect(remoteEndPoint);
                connected = true;
        }
         

        private void send()
        {
                    command++;
                    char output = (char)command;
                    Object objData = (output) & (char)0;
                    byte[] byData = System.Text.Encoding.ASCII.GetBytes(objData.ToString());
                    m_socWorker.Send(byData);
                    }

Toelichting: Command is hier gewoon een int, tussen de 0 en 255 die moet worden verstuurd net als bij de visual basic code. Bij beiden moet dit dus gebeuren naar ip: "192.168.1.1" en poort 1500

Hij geeft geen foutmeldingen met de C# code, dus op zich lijkt de verbinding wel te lukken, het juist verzenden denk ik alleen niet.

Ik hoop dat het voor jullie wel duidelijk is

[ Voor 22% gewijzigd door huub8 op 08-02-2011 15:35 ]


Acties:
  • 0 Henk 'm!

  • Down
  • Registratie: Februari 2005
  • Laatst online: 07:07
Verder debuggen. Wordt er uberhaupt iets over het lijntje gestuurd? Gebruik netstat eens (cmd-> netstat) om te kijken wat er gebeurt met je verbinding?

Mother north, how can they sleep while their beds are burning?


Acties:
  • 0 Henk 'm!

  • huub8
  • Registratie: Maart 2009
  • Laatst online: 28-06-2021
Netstat geeft dit (eerste zonder dat vb6 of C# met de router is verbonden, tweede met aleen C# verbonden, derde met alleen vb6 verbonden)

C:\Documents and Settings\Huub>netstat

Actieve verbindingen

Proto Lokaal adres Extern adres Status
TCP HuubLaptop:1045 localhost:1046 ESTABLISHED
TCP HuubLaptop:1046 localhost:1045 ESTABLISHED
TCP HuubLaptop:1048 localhost:1049 ESTABLISHED
TCP HuubLaptop:1049 localhost:1048 ESTABLISHED
TCP HuubLaptop:1951 localhost:2869 ESTABLISHED
TCP HuubLaptop:2869 localhost:1951 ESTABLISHED
TCP HuubLaptop:5152 localhost:1047 CLOSE_WAIT

C:\Documents and Settings\Huub>netstat

Actieve verbindingen

Proto Lokaal adres Extern adres Status
TCP HuubLaptop:1045 localhost:1046 ESTABLISHED
TCP HuubLaptop:1046 localhost:1045 ESTABLISHED
TCP HuubLaptop:1048 localhost:1049 ESTABLISHED
TCP HuubLaptop:1049 localhost:1048 ESTABLISHED
TCP HuubLaptop:1951 localhost:2869 ESTABLISHED
TCP HuubLaptop:2869 localhost:1951 ESTABLISHED
TCP HuubLaptop:5152 localhost:1047 CLOSE_WAIT
TCP HuubLaptop:1952 192.168.1.1:1500 ESTABLISHED

C:\Documents and Settings\Huub>netstat

Actieve verbindingen

Proto Lokaal adres Extern adres Status
TCP HuubLaptop:1045 localhost:1046 ESTABLISHED
TCP HuubLaptop:1046 localhost:1045 ESTABLISHED
TCP HuubLaptop:1048 localhost:1049 ESTABLISHED
TCP HuubLaptop:1049 localhost:1048 ESTABLISHED
TCP HuubLaptop:1951 localhost:2869 ESTABLISHED
TCP HuubLaptop:2869 localhost:1951 ESTABLISHED
TCP HuubLaptop:5152 localhost:1047 CLOSE_WAIT
TCP HuubLaptop:1954 192.168.1.1:1500 ESTABLISHED

C:\Documents and Settings\Huub>

Acties:
  • 0 Henk 'm!

  • urk_forever
  • Registratie: Juni 2001
  • Laatst online: 22-09 16:04
Staat de socket niet te wachten totdat de SendBuffer vol is voordat hij het verstuurd?

Hail to the king baby!


Acties:
  • 0 Henk 'm!

  • huub8
  • Registratie: Maart 2009
  • Laatst online: 28-06-2021
ik denk dat dat inderdaad ook een probleem was, maar ook na toevoegen van
m_socWorker.SendBufferSize = 1;

Werkt het nog niet.

Acties:
  • 0 Henk 'm!

  • MLM
  • Registratie: Juli 2004
  • Laatst online: 12-03-2023

MLM

aka Zolo

code:
1
2
3
char output = (char)command;
Object objData = (output) & (char)0;
byte[] byData = System.Text.Encoding.ASCII.GetBytes(objData.ToString());


Ik weet niet of het je probleem is, maar op de tweede regel van bovenstaande quote doe je een logical AND met 0, dat resulteert ALTIJD in een 0. (in VB6 is de &-operator string concatenation). Daarnaast, een char in C# is een wide character, ik weet niet of die encode naar ASCII wel lekker werkt?

Je VB6 code verzend dus >2< bytes, de eerste byte met waarde (output + 1), en de tweede met waarde 0.
Je C# code verzend dus >1< byte, met de waarde 0.

C# code zou ipv met char, met byte moeten werken, en lijken op iets als:
code:
1
2
3
byte[] byData = new byte[2];
data[0] = (byte)command;
data[1] = 0;


Daarnaast, SendBufferSize staat standaard op 8K, en dat is een prima size. Zelfs als de implemetatie SendBufferSize van 1 zou toelaten, is het een enorm inefficiente waarde, omdat ie buffers moet flushen voor elke byte die je verzend. TCP is een streaming protocol, het regelt zelf wel wanneer het pakketjes bouwt van jouw >STREAM<, jezelf daar tegenaan bemoeien is in 99% van de gevallen geen goed idee, dus dat zou ik in elk geval NIET doen.
quote: MSDN
If you are using a connection-oriented protocol, Send will block until all of the bytes in the buffer are sent, unless a time-out was set by using Socket::SendTimeout.
Dus als je Send geen exception gooit, mag je er van uit gaan dat je data word verzonden.

[ Voor 32% gewijzigd door MLM op 08-02-2011 16:38 ]

-niks-


Acties:
  • 0 Henk 'm!

  • huub8
  • Registratie: Maart 2009
  • Laatst online: 28-06-2021
De code werkt zo inderdaad bijna perfect. Het enige probleem is nu dat de ledjes die worden aangestuurt door de microcontroller wanneer een bepaald signaal aankomt nu inderdaad wel aangaan, maar dan al snel kort uit om daarna wel aan te blijven.

Alsof het signaal dus weer even nul werd.

Acties:
  • 0 Henk 'm!

  • MLM
  • Registratie: Juli 2004
  • Laatst online: 12-03-2023

MLM

aka Zolo

Ik zou bijna zeggen dat die 0-byte het probleem zou zijn, maar dat verklaart niet waarom daarna alsnog de juiste waarde word gebruikt (gezien de 0-byte de laatste byte is). Je kan eens packet-inspecten en kijken of er een verschil is in de data danwel timing van je data tussen vb6 en c#. En anders heb je een probleem aan de ontvangende kant waarschijnlijk.

-niks-

Pagina: 1