Question

Je dois être en mesure d'envoyer un message UDP et également recevoir un pour découvrir les périphériques SSDP sur le réseau de l'iPhone.

Je sais que je dois envoyer le paquet à l'adresse de multidiffusion et mes besoins de requête HTTP à ressembler à quelque chose comme ceci:

M-SEARCH * HTTP/1.1
Host: 239.255.255.250:1900
Man: ssdp:discover
Mx: 3
ST: "urn:schemas-upnp-org:device:InternetGatewayDevice:1"

De la lecture des documents, il semble que je peux faire tout cela avec CFNetwork et malgré la lecture (et relire les documents) Je me bats pour commencer. Quelqu'un peut-il recommander et des tutoriels ou des extraits de code pour me faire sur la bosse d'apprentissage initiale?

J'ai le guide de programmation CFNetwork:

http://developer.apple.com/ mac / bibliothèque / documentation / réseau / conceptuel / CFNetwork / CFNetwork.pdf

et le Guide de Beej à la programmation réseau en utilisant une connexion Internet filaire:

http://beej.us/guide/bgnet/

Merci

Dave

P.S.

Je ne peux pas utiliser les bibliothèques 3ème partie et des cadres dans ce cas.

Était-ce utile?

La solution 3

OK, enfin fait. Trouvé une classe dans le domaine public (merci Chris) appelé AsyncUdpSocket qui vous permet de créer une socket UDP que vous pouvez ensuite activer la diffusion et joindre l'adresse de multidiffusion.

Il y a une belle méthode sendData, avec l'ajout d'une boucle de course pour empêcher le blocage.

L'espoir qui aide.

Dave

Autres conseils

J'ai utilisé avec succès AsyncUdpSocket pour exécuter SSDP Discovery et trouver les contrôleurs. Voici mes extraits de code:

Initialiser et configurer le socket:

//  AsyncUdpSocket *ssdpSock = [[AsyncUdpSocket alloc] initWithDelegate:self];
    AsyncUdpSocket *ssdpSock = [[AsyncUdpSocket alloc] initIPv4];
    [ssdpSock setDelegate:self];

Notez la première ligne commentée. J'ai trouvé sur les forums AsyncUdpSocket quelques problèmes avec les doublons. Je ne pense pas que je les ai confronté mais je de toute façon.

J'ai ajouté la vérification des erreurs, et il a été utile parce que pendant mon débogage je ne ferme pas prises et j'ai commencé à des échecs de configuration socket:

NSError *socketError = nil;

    if (![ssdpSock bindToPort:1900 error:&socketError]) {
        NSLog(@"Failed binding socket: %@", [socketError localizedDescription]);
        return statusController;
    }

    if(![ssdpSock joinMulticastGroup:@"239.255.255.250" error:&socketError]){
        NSLog(@"Failed joining multicast group: %@", [socketError localizedDescription]);
        return statusController;
    }

    if (![ssdpSock enableBroadcast:TRUE error:&socketError]){
        NSLog(@"Failed enabling broadcast: %@", [socketError localizedDescription]);
        return statusController;
    }

    [ssdpSock sendData:[self.discoverControllerString dataUsingEncoding:NSUTF8StringEncoding]
                toHost:@"239.255.255.250"
                  port:1900
           withTimeout:2
                   tag:1];

Remarquez les changements que j'ai apportées au temps. Et puis finalement fait la Param.RC, et fermé la prise. Notez la fermeture du socket. Depuis que je suis dans ma propre classe quand je courais ce -. Le code ci-dessus ne fait le travail pour moi

[ssdpSock receiveWithTimeout: 2 tag:1];
    [NSTimer scheduledTimerWithTimeInterval: 5 target: self 
                                   selector:@selector(completeSearch:) userInfo: self repeats: NO]; 





    [ssdpSock closeAfterSendingAndReceiving];

Le changement le plus important a probablement été le retour « NON » si je ne l'ai pas trouvé mon contrôleur. Le premier RECEVOIR était d'ailleurs le message de découverte elle-même revenir. Et quand je l'ai lu dans le fichier AsyncUdpSocket.h soigneusement - retour « NON » quand il est pas un paquet que vous cherchez aidé

.

Notez également que je me sers ARC dans mon code, mais je compila les AsyncUdpSocket sans support ARC.

-(void) completeSearch: (NSTimer *)t 
{

    NSLog(@"%s",__FUNCTION__);

    //[ssdpSock close];
    //ssdpSock = nil;

}


- (BOOL)onUdpSocket:(AsyncUdpSocket *)sock 
     didReceiveData:(NSData *)data 
            withTag:(long)tag 
           fromHost:(NSString *)host 
               port:(UInt16)port
{
    NSLog(@"%s %ld %@ %d",__FUNCTION__,tag,host,port);
    NSString *aStr = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];

    NSLog(@"%@",aStr);



    NSString *compareString = [aStr stringByPaddingToLength:[self.responseString length] withString:@"." startingAtIndex:0];
    //NSLog(@"%@", compareString);
    //NSLog(@"%@", self.responseString);

    if ([compareString isEqualToString:self.responseString])
    {
        NSLog(@"String Compare, Controller Found!");
        [self.controllerList addObject:aStr];
        //NSData *controllerIP = [aStr dataUsingEncoding:NSUTF8StringEncoding];
        [[NSNotificationCenter defaultCenter] postNotificationName:@"DiscoveredController" object:nil];


        return YES;
    }

    return NO;

}

Je le code suivant pour la recherche SSDP dans mon application:

-(void)discoverDevices {
ssdpSock = [[AsyncUdpSocket alloc] initWithDelegate:self];
[ssdpSock enableBroadcast:TRUE error:nil];
NSString *str = @"M-SEARCH * HTTP/1.1\r\nHOST: 239.255.255.250:1900\r\nMan: \"ssdp:discover\"\r\nST: mydev\r\n\r\n";    
[ssdpSock bindToPort:0 error:nil];
[ssdpSock joinMulticastGroup:@"239.255.255.250" error:nil];
[ssdpSock sendData:[str dataUsingEncoding:NSUTF8StringEncoding] 
         toHost: @"239.255.255.250" port: 1900 withTimeout:-1 tag:1];
[ssdpSock receiveWithTimeout: -1 tag:1];
[NSTimer scheduledTimerWithTimeInterval: 5 target: self 
           selector:@selector(completeSearch:) userInfo: self repeats: NO]; }


-(void) completeSearch: (NSTimer *)t {
NSLog(@"%s",__FUNCTION__);
[ssdpSock close];
ssdpSock = nil;}

- (BOOL)onUdpSocket:(AsyncUdpSocket *)sock didReceiveData:(NSData *)data withTag:(long)tag fromHost:(NSString *)host port:(UInt16)port{
NSLog(@"%s %d %@ %d",__FUNCTION__,tag,host,port);
NSString *aStr = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
NSLog(@"%@",aStr);}

Il utilise le AsyncUdpSocket de CocoaAsyncSocket .

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top