.NET Sockets

WorldRacer

Erfahrenes Mitglied
Hallo Leute ich bins wieder ;)

also, hab folgenden Code erstmal:

Code:
System::Net::Sockets::TcpClient^ client = gcnew System::Net::Sockets::TcpClient("10.0.100.137", 9999);
				 System::String^ blubb = "blubb";
				 array<Byte>^ data = System::Text::Encoding::ASCII->GetBytes(blubb);
				 System::Net::Sockets::NetworkStream^ stream = client->GetStream();
      
				 // Send the message to the connected TcpServer. 
				 stream->Write( data, 0, data->Length );

Das wäre mein Code zum Senden eines schlichten "Blubb" an einen Netzwerkserver mit der IP 10.0.100.137 (z.B.) und dem Port 9999. Wenn ich diesen Schnipsel aud einen SDL_net Server anwende erhalte ich hinterher (in dem Konsolenfenster) ein

blubb??????????
????????????????????????????????????????????????????????????????????????????????
????????????????????????????????????????????????????????????????????????????????
????????????????????????????????????????????????????????????????????????????????
????????????????????????????????????????????????????????????????????????????????
????????????????????????????????????????????????????????????????????????????????
????????????????????????????????????????????????????????????????????????????????
?????????????????????????Xdì

statt ein

Warum? kann mir das einer erklären? Von SDL_net-Client -> SDL_net-Server gehts einwandfrei, nur mit einem .NET Clienten halt net. Ich kann leider net auf einen SDL_net Server verzichten, da ich (ausser ihr schlagt mir eine auf Linux passende variante vor) den Server auf Linux installieren möchte.

Vielen Dank im Voraus!

WR
 

WorldRacer

Erfahrenes Mitglied
Hab schon eine Lösung, danke trotzdem. Hab mit Hile eines Tutorials auf das Linux-Original zugegriffen. Poste euch gleich dann den objektorientierten Code.

So es ist soweit:

Code:
 /* >> SocketHelper Class << Marco Klein, 18.01.2009 11:44

         This class gives you the possibility to use
         linux sockets the easy way. What you have to do is:
                 -> Include SocketHelper.h
                 -> Initialize 'SocketHelper' class
                 -> Call the 'OpenSocket' method
                 -> Call the 'Listen' method
                 -> Then call the 'RecieveData' method.
                 -> To get your message you have to:
                         > Call the 'CopyMessage' method
                         > Then get your char[256] of the class named 'Message'
                 -> If you want to, you can 'Answer' a char* to your client with
                    the Answer method.

         To close your connection, use "CloseSocket"

         You have to include the following headers:
                 #include <cstdlib>
                 #include <stdio.h>
                 #include <stdlib.h>
                 #include <iostream>
                 #include <fstream>
                 #include <sys/types.h>
                 #include <sys/socket.h>
                 #include <netinet/in.h>
                 #include <string.h>

         Have Fun 

         c) 2009 by WorldRacer, http://www.devforyou.de
                                                                         */

#define SH_READY_FOR_LISTENING   1
#define SH_ACCEPT_FAILED         1
#define SH_ERROR_OPENING_SOCKET  1
#define SH_ERROR_BINDING         1
#define SH_ERROR_READING_SOCKET  1
#define SH_ERROR_SENDING_MSG     1
#define SH_NOT_ALLOWED_YET       1
using namespace std;
class SocketHelper {
         public:
                 SocketHelper(int port);
                 int Listen(void);
                 int OpenSocket(void);
                 int RetrieveMessage(void);
                 int Answer(char *data);
                 int CopyMessage(void);
                 char Message[256];
                 int CloseSocket(void);
         private:
                  int status;
                  int sockfd, newsockfd, portno, clilen, n;
                  char buffer[256];
                  struct sockaddr_in serv_addr, cli_addr;


};
SocketHelper::SocketHelper(int port){
         this->portno = port;
         this->status = 0;
         Message[0] = 'N';
         Message[1] = 'O';
         Message[2] = '_';
         Message[3] = 'M';
         Message[4] = 'E';
         Message[5] = 'S';
         Message[6] = 'S';
         Message[7] = 'A';
         Message[8] = 'G';
         Message[9] = 'E';
         Message[10] = '_';
         Message[11] = 'C';
         Message[12] = 'O';
         Message[13] = 'P';
         Message[14] = 'I';
         Message[15] = 'E';
         Message[16] = 'D';
         Message[17] = '\0';
}
int SocketHelper::OpenSocket(void){
         this->sockfd = socket(AF_INET, SOCK_STREAM, 0);
         if (this->sockfd < 0)
                 return 1;

         bzero((char *) &this->serv_addr, sizeof(this->serv_addr));
         this->serv_addr.sin_family = AF_INET;
         this->serv_addr.sin_port = htons(portno);
         this->serv_addr.sin_addr.s_addr = INADDR_ANY;
         if (bind(this->sockfd, (struct sockaddr *) &this->serv_addr, sizeof(this->serv_addr)) < 0){
                 return 2;
         }
         this->status = 1;
         return 0;
}
int SocketHelper::Listen(void){
         if(this->status != 1){
                 return 3;
         }
         this->status = 2;
         listen(this->sockfd,5);
}
int SocketHelper::RetrieveMessage(void){
         int error;
         if(this->status != 2){
                 return 3;
         }
         this->clilen = sizeof(this->cli_addr);
         this->newsockfd = accept(this->sockfd, (struct sockaddr *) &this->cli_addr, (socklen_t *) &this->clilen);
         if (this->newsockfd < 0){
                 return 1;
         }
         bzero(this->buffer,255);
         this->n = read(this->newsockfd,this->buffer,255);
         if (this->n < 0){
                 return 2;
         }
         return 0;
}
int stringlength(char *s)
{
         int len=0;
         while(*s !=0)
         {
                 len++;
                 s++;
         }
         return len;
}
int SocketHelper::Answer(char *data){
         this->n = write(this->newsockfd,data,stringlength(data));
         if (this->n < 0) return 1;
         return 0;
}
int SocketHelper::CloseSocket(void){
         return close(this->sockfd);
}
int SocketHelper::CopyMessage(void){
         int i;
         for(i=0; i<=255; i++){
                 this->Message[i] = this->buffer[i];
         }
         return 0;
}

Das ist der Code für die Socket-Klasse. Hier nun ein Beispiel:

Code:
#include <cstdlib>
#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <fstream>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <string.h>
#include "include/SocketHelper.h"
using namespace std;
void error(char *msg)
{
  perror(msg);
  exit(1);
}
int main(int argc, char *argv[])
{
  int returnval;

  if (argc < 2)
  {
         fprintf(stderr,"ERROR, no port provided\n");
         exit(1);
  }

  SocketHelper sh(atoi(argv[1]));
  returnval = sh.OpenSocket();
  if(returnval == SH_ERROR_OPENING_SOCKET ){
         error("ERROR opening socket\n");
  }
  if(returnval == SH_ERROR_BINDING ){
         error("ERROR on binding\n");
  }
  returnval = sh.Listen();
  if(returnval == SH_NOT_ALLOWED_YET){
         error("Calling the function is not allowed at the moment.");
  }
  returnval = sh.RetrieveMessage();
  if(returnval == SH_ACCEPT_FAILED){
         error("ERROR on accept");
  }
  if(returnval == SH_ERROR_READING_SOCKET){
         error("ERROR reading from socket");
  }
  returnval = sh.CopyMessage();
  printf("Here is the message: %s%s",sh.Message,"\n");

  returnval = sh.Answer("I got your Message");
  if(returnval == SH_ERROR_SENDING_MSG){
         error("ERROR writing to socket");
  }
  return 0;
}
 
Zuletzt bearbeitet:

WorldRacer

Erfahrenes Mitglied
Aber eine Frage hätt ich da noch. Ich hab einen Clienten vom Typ TcpClient der von mehreren Forms genutzt werden soll... Wie stell ich das an, dass alle auf die gleiche Instanz zugreifen?
 

Nico Graichen

Erfahrenes Mitglied
Hi

Das kannst du, in dem du dir ein Klasse schaffst, die die Kommunikation mit dem Server übernimmt und du die Instanz in allen Forms bekannt machst.
Du solltest dann jedoch darauf achten, dass diese Klasse Thread-stabil ist, da du konkurierende Zugriffe haben kannst.
 

Neue Beiträge