web-dev-qa-db-fra.com

Prise UDP au webassembly

J'essaie de porter mon application de bureau écrite en C et C++ sur la plate-forme Webassembly et je cherche à savoir si c'est possible. L’une des tâches importantes de l’application est de communiquer en envoyant et en recevant des messages UDP. J'ai implémenté un client UDP minimal qui crée simplement un socket UDP et envoie des paquets au serveur (construit de manière native et exécuté en tant qu'exécutable séparé sur le même ordinateur). Les API socket, bind et sendto ne renvoient aucune erreur et tout semble bien fonctionner, mais aucun message n'est reçu côté serveur, et wireshark n'affiche aucune activité sur ce port.

Le socket UDP est-il simplement stubé sur le port Webassembly libc ou est-il implémenté au-dessus d’une connexion Web standard (par exemple, WebRTC)?

Le code client est ci-dessous. J'ai vérifié que la construction native fonctionne correctement.

#include <stdlib.h>
#include <string.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <unistd.h>

#define BUFLEN 512
#define NPACK 100
#define PORT 9930

void diep(char *s)
{
  perror(s);
  exit(1);
}

#define SRV_IP "127.0.0.1"


int main(void)
{
  struct sockaddr_in si_other;
  int s, i, slen=sizeof(si_other);
  char buf[BUFLEN];

  if ((s=socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP))==-1)
    diep("socket");

  memset((char *) &si_other, 0, sizeof(si_other));
  si_other.sin_family = AF_INET;
  si_other.sin_port = htons(PORT);
  if (inet_aton(SRV_IP, &si_other.sin_addr)==0) {
    fprintf(stderr, "inet_aton() failed\n");
    exit(1);
  }

  for (i=0; i<NPACK; i++) {
    printf("Sending packet %d\n", i);
    sprintf(buf, "This is packet %d\n", i);
    if (sendto(s, buf, BUFLEN, 0, (struct sockaddr*)&si_other, slen)==-1)
      diep("sendto()");
  }

  close(s);
  return 0;
}

J'ai suivi les instructions de http://webassembly.org/getting-started/developers-guide/ pour le construire et l'exécuter.

Merci d'avance pour toute aide ou des indices!

7
roof

Tout ce qui s'exécute dans le navigateur ne vous donnera pas d'accès à un socket natif et je soupçonne que les éditeurs de navigateurs s'opposeraient vivement à un tel accès car il s'agit d'une violation potentielle de la sécurité.

Peut-être que de plus en plus d'applications natives se déplacent vers le Web alors que la différence de performances se réduit en raison de webassembly et d'initiatives similaires les inciteraient à changer de position, mais jusque-là, tout ce qui veut un contrôle direct par socket devrait rester une application native.

2
Adnan Y

J'ai trouvé comment les sockets UDP sont implémentés au webassembly. En fait, ils sont imités par les websockets. Cela fonctionnerait probablement si le client et le serveur étaient des assemblages Web, mais mon serveur est construit nativement. Comme wasm ne prend pas en charge les liens dynamiques, tout le code (y compris l’implémentation libc) est regroupé dans un fichier JS, si nous pouvons trouver une implémentation UDP sendto:

// if we're emulating a connection-less dgram socket and don't have
      // a cached connection, queue the buffer to send upon connect and
      // lie, saying the data was sent now.
      if (sock.type === 2) {
        if (!dest || dest.socket.readyState !== dest.socket.OPEN) {
          // if we're not connected, open a new connection
          if (!dest || dest.socket.readyState === dest.socket.CLOSING || dest.socket.readyState === dest.socket.CLOSED) {
            dest = SOCKFS.websocket_sock_ops.createPeer(sock, addr, port);
          }
          dest.dgram_send_queue.Push(data);
          return length;
        }
      }
2
roof