Changeset 842 in ntrip for trunk/ntripclient
- Timestamp:
- Apr 22, 2008, 4:26:44 PM (17 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/ntripclient/ntripclient.c
r834 r842 1 1 /* 2 2 NTRIP client for POSIX. 3 $Id: ntripclient.c,v 1.4 2 2008/04/07 11:49:13stoecker Exp $3 $Id: ntripclient.c,v 1.43 2008/04/15 13:27:49 stoecker Exp $ 4 4 Copyright (C) 2003-2008 by Dirk Stöcker <soft@dstoecker.de> 5 5 … … 59 59 60 60 /* CVS revision and version */ 61 static char revisionstr[] = "$Revision: 1.4 2$";62 static char datestr[] = "$Date: 2008/04/ 07 11:49:13$";61 static char revisionstr[] = "$Revision: 1.43 $"; 62 static char datestr[] = "$Date: 2008/04/15 13:27:49 $"; 63 63 64 64 enum MODE { HTTP = 1, RTSP = 2, NTRIP1 = 3, AUTO = 4, END }; … … 85 85 enum SerialProtocol protocol; 86 86 const char *serdevice; 87 const char *serlogfile; 87 88 }; 88 89 … … 112 113 { "parity", required_argument, 0, 'Y'}, 113 114 { "databits", required_argument, 0, 'A'}, 115 { "serlogfile", required_argument, 0, 'l'}, 114 116 { "help", no_argument, 0, 'h'}, 115 117 {0,0,0,0}}; 116 118 #endif 117 #define ARGOPT "-d:m:bhp:r:s:u:n:S:R:M:IP:D:B:T:C:Y:A: "119 #define ARGOPT "-d:m:bhp:r:s:u:n:S:R:M:IP:D:B:T:C:Y:A:l:" 118 120 119 121 int stop = 0; … … 150 152 while(*req && urlenc < bufend) 151 153 { 152 if(isalnum(*req) 154 if(isalnum(*req) 153 155 || *req == '-' || *req == '_' || *req == '.') 154 156 *urlenc++ = *req++; … … 187 189 else 188 190 { 189 while(*url && *url != '@' && *url != '/' && Buffer != Bufend) 191 while(*url && *url != '@' && *url != '/' && Buffer != Bufend) 190 192 { 191 193 if(isalnum(*url) || *url == '-' || *url == '_' || *url == '.') … … 320 322 args->baud = SPABAUD_9600; 321 323 args->serdevice = 0; 324 args->serlogfile = 0; 322 325 help = 0; 323 326 … … 333 336 case 'u': args->user = optarg; break; 334 337 case 'p': args->password = optarg; break; 335 case 'd': 338 case 'd': /* legacy option, may get removed in future */ 339 fprintf(stderr, "Option -d or --data is deprecated. Use -m instead.\n"); 336 340 case 'm': 337 if(optarg && *optarg == '?') 341 if(optarg && *optarg == '?') 338 342 args->data = encodeurl(optarg); 339 else 340 args->data = optarg; 343 else 344 args->data = optarg; 341 345 break; 342 346 case 'B': … … 408 412 break; 409 413 case 'D': args->serdevice = optarg; break; 414 case 'l': args->serlogfile = optarg; break; 410 415 case 'I': args->initudp = 1; break; 411 416 case 'P': args->udpport = strtol(optarg, 0, 10); break; … … 469 474 " -r " LONG_OPT("--port ") "the server port number (default 2101)\n" 470 475 " -u " LONG_OPT("--user ") "the user name\n" 471 " -n " LONG_OPT("--nmea ") "NMEA string for sending to server\n"472 " -b " LONG_OPT("--bitrate ") "output bitrate\n"473 " -I " LONG_OPT("--initudp ") "send initial UDP packet for firewall handling\n"474 " -P " LONG_OPT("--udpport ") "set the local UDP port\n"475 " -S " LONG_OPT("--proxyhost ") "proxy name or address\n"476 " -R " LONG_OPT("--proxyport ") "proxy port, optional (default 2101)\n"477 " -D " LONG_OPT("--serdevice ") "serial device for output\n"478 " -B " LONG_OPT("--baud ") "baudrate for serial device\n"479 " -T " LONG_OPT("--stopbits ") "stopbits for serial device\n"480 " -C " LONG_OPT("--protocol ") "protocol for serial device\n"481 " -Y " LONG_OPT("--parity ") "parity for serial device\n"482 " -A " LONG_OPT("--databits ") "databits for serial device\n"483 476 " -M " LONG_OPT("--mode ") "mode for data request\n" 484 477 " Valid modes are:\n" … … 488 481 " 4, a, auto automatic detection (default)\n" 489 482 "or using an URL:\n%s ntrip:mountpoint[/user[:password]][@[server][:port][@proxyhost[:proxyport]]][;nmea]\n" 483 "\nExpert options:\n" 484 " -n " LONG_OPT("--nmea ") "NMEA string for sending to server\n" 485 " -b " LONG_OPT("--bitrate ") "output bitrate\n" 486 " -I " LONG_OPT("--initudp ") "send initial UDP packet for firewall handling\n" 487 " -P " LONG_OPT("--udpport ") "set the local UDP port\n" 488 " -S " LONG_OPT("--proxyhost ") "proxy name or address\n" 489 " -R " LONG_OPT("--proxyport ") "proxy port, optional (default 2101)\n" 490 "\nSerial input/output:\n" 491 " -D " LONG_OPT("--serdevice ") "serial device for output\n" 492 " -B " LONG_OPT("--baud ") "baudrate for serial device\n" 493 " -T " LONG_OPT("--stopbits ") "stopbits for serial device\n" 494 " -C " LONG_OPT("--protocol ") "protocol for serial device\n" 495 " -Y " LONG_OPT("--parity ") "parity for serial device\n" 496 " -A " LONG_OPT("--databits ") "databits for serial device\n" 497 " -l " LONG_OPT("--serlogfile ") "logfile for serial data\n" 490 498 , revisionstr, datestr, argv[0], argv[0]); 491 499 exit(1); … … 566 574 { 567 575 struct serial sx; 576 FILE *ser = 0; 568 577 char nmeabuffer[200] = "$GPGGA,"; /* our start string */ 569 578 size_t nmeabufpos = 0; … … 579 588 return 20; 580 589 } 590 if(args.serlogfile) 591 { 592 if(!(ser = fopen(args.serlogfile, "a+"))) 593 { 594 SerialFree(&sx); 595 fprintf(stderr, "Could not open serial logfile.\n"); 596 return 20; 597 } 598 } 581 599 } 582 600 do 583 601 { 584 sockettype sockfd; 585 int numbytes; 602 int error = 0; 603 sockettype sockfd = 0; 604 int numbytes; 586 605 char buf[MAXDATASIZE]; 587 606 struct sockaddr_in their_addr; /* connector's address information */ … … 616 635 { 617 636 fprintf(stderr, "Can't resolve port %s.", args.port); 618 exit(1);637 stop = 1; 619 638 } 620 639 else … … 622 641 p = ntohs(se->s_port); 623 642 } 624 snprintf(proxyport, sizeof(proxyport), "%d", p); 625 port = args.proxyport; 626 proxyserver = args.server; 627 server = args.proxyhost; 643 if(!stop && !error) 644 { 645 snprintf(proxyport, sizeof(proxyport), "%d", p); 646 port = args.proxyport; 647 proxyserver = args.server; 648 server = args.proxyhost; 649 } 628 650 } 629 651 else … … 632 654 port = args.port; 633 655 } 634 memset(&their_addr, 0, sizeof(struct sockaddr_in)); 635 if((i = strtol(port, &b, 10)) && (!b || !*b)) 636 their_addr.sin_port = htons(i); 637 else if(!(se = getservbyname(port, 0))) 638 { 639 fprintf(stderr, "Can't resolve port %s.", port); 640 exit(1); 641 } 642 else 643 { 644 their_addr.sin_port = se->s_port; 645 } 646 if(!(he=gethostbyname(server))) 647 { 648 fprintf(stderr, "Server name lookup failed for '%s'.\n", server); 649 exit(1); 650 } 651 if((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1) 652 { 653 perror("socket"); 654 exit(1); 655 } 656 their_addr.sin_family = AF_INET; 657 their_addr.sin_addr = *((struct in_addr *)he->h_addr); 658 659 if(args.data && *args.data != '%' && args.mode == RTSP) 660 { 661 struct sockaddr_in local; 662 int sockudp, localport; 663 int cseq = 1; 664 socklen_t len; 665 666 if((sockudp = socket(AF_INET, SOCK_DGRAM, 0)) == -1) 656 if(!stop && !error) 657 { 658 memset(&their_addr, 0, sizeof(struct sockaddr_in)); 659 if((i = strtol(port, &b, 10)) && (!b || !*b)) 660 their_addr.sin_port = htons(i); 661 else if(!(se = getservbyname(port, 0))) 667 662 { 668 perror("socket"); 669 exit(1); 670 } 671 /* fill structure with local address information for UDP */ 672 memset(&local, 0, sizeof(local)); 673 local.sin_family = AF_INET; 674 local.sin_port = htons(args.udpport); 675 local.sin_addr.s_addr = htonl(INADDR_ANY); 676 len = sizeof(local); 677 /* bind() in order to get a random RTP client_port */ 678 if((bind(sockudp, (struct sockaddr *)&local, len)) < 0) 679 { 680 perror("bind"); 681 exit(1); 682 } 683 if((getsockname(sockudp, (struct sockaddr*)&local, &len)) != -1) 684 { 685 localport = ntohs(local.sin_port); 663 fprintf(stderr, "Can't resolve port %s.", port); 664 stop = 1; 686 665 } 687 666 else 688 667 { 689 perror("local access failed"); 690 exit(1); 668 their_addr.sin_port = se->s_port; 691 669 } 692 if(connect(sockfd, (struct sockaddr *)&their_addr, 693 sizeof(struct sockaddr)) == -1) 670 if(!stop && !error) 694 671 { 695 perror("connect"); 696 exit(1); 697 } 698 i=snprintf(buf, MAXDATASIZE-40, /* leave some space for login */ 699 "SETUP rtsp://%s%s%s/%s RTSP/1.0\r\n" 700 "CSeq: %d\r\n" 701 "Ntrip-Version: Ntrip/2.0\r\n" 702 "Ntrip-Component: Ntripclient\r\n" 703 "User-Agent: %s/%s\r\n" 704 "Transport: RTP/GNSS;unicast;client_port=%u\r\n" 705 "Authorization: Basic ", 706 args.server, proxyserver ? ":" : "", proxyserver ? args.port : "", 707 args.data, cseq++, AGENTSTRING, revisionstr, localport); 708 if(i > MAXDATASIZE-40 || i < 0) /* second check for old glibc */ 709 { 710 fprintf(stderr, "Requested data too long\n"); 711 exit(1); 712 } 713 i += encode(buf+i, MAXDATASIZE-i-4, args.user, args.password); 714 if(i > MAXDATASIZE-4) 715 { 716 fprintf(stderr, "Username and/or password too long\n"); 717 exit(1); 718 } 719 buf[i++] = '\r'; 720 buf[i++] = '\n'; 721 buf[i++] = '\r'; 722 buf[i++] = '\n'; 723 if(args.nmea) 724 { 725 int j = snprintf(buf+i, MAXDATASIZE-i, "%s\r\n", args.nmea); 726 if(j >= 0 && j < MAXDATASIZE-i) 727 i += j; 672 if(!(he=gethostbyname(server))) 673 { 674 fprintf(stderr, "Server name lookup failed for '%s'.\n", server); 675 error = 1; 676 } 677 else if((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1) 678 { 679 perror("socket"); 680 error = 1; 681 } 728 682 else 729 683 { 730 fprintf(stderr, "NMEA string too long\n");731 exit(1);684 their_addr.sin_family = AF_INET; 685 their_addr.sin_addr = *((struct in_addr *)he->h_addr); 732 686 } 733 687 } 734 if(send(sockfd, buf, (size_t)i, 0) != i) 688 } 689 if(!stop && !error) 690 { 691 if(args.data && *args.data != '%' && args.mode == RTSP) 735 692 { 736 perror("send"); 737 exit(1); 738 } 739 if((numbytes=recv(sockfd, buf, MAXDATASIZE-1, 0)) != -1) 740 { 741 if(numbytes >= 17 && !strncmp(buf, "RTSP/1.0 200 OK\r\n", 17)) 693 struct sockaddr_in local; 694 sockettype sockudp = 0; 695 int localport; 696 int cseq = 1; 697 socklen_t len; 698 699 if((sockudp = socket(AF_INET, SOCK_DGRAM, 0)) == -1) 742 700 { 743 int serverport = 0, session = 0; 744 const char *portcheck = "server_port="; 745 const char *sessioncheck = "session: "; 746 int l = strlen(portcheck)-1; 747 int j=0; 748 for(i = 0; j != l && i < numbytes-l; ++i) 749 { 750 for(j = 0; j < l && tolower(buf[i+j]) == portcheck[j]; ++j) 751 ; 752 } 753 if(i == numbytes-l) 754 { 755 fprintf(stderr, "No server port number found\n"); 756 exit(1); 757 } 758 else 759 { 760 i+=l; 761 while(i < numbytes && buf[i] >= '0' && buf[i] <= '9') 762 serverport = serverport * 10 + buf[i++]-'0'; 763 if(buf[i] != '\r' && buf[i] != ';') 701 perror("socket"); 702 error = 1; 703 } 704 if(!stop && !error) 705 { 706 /* fill structure with local address information for UDP */ 707 memset(&local, 0, sizeof(local)); 708 local.sin_family = AF_INET; 709 local.sin_port = htons(args.udpport); 710 local.sin_addr.s_addr = htonl(INADDR_ANY); 711 len = sizeof(local); 712 /* bind() in order to get a random RTP client_port */ 713 if((bind(sockudp, (struct sockaddr *)&local, len)) < 0) 714 { 715 perror("bind"); 716 error = 1; 717 } 718 else if((getsockname(sockudp, (struct sockaddr*)&local, &len)) == -1) 719 { 720 perror("local access failed"); 721 error = 1; 722 } 723 else if(connect(sockfd, (struct sockaddr *)&their_addr, 724 sizeof(struct sockaddr)) == -1) 725 { 726 perror("connect"); 727 error = 1; 728 } 729 localport = ntohs(local.sin_port); 730 } 731 if(!stop && !error) 732 { 733 i=snprintf(buf, MAXDATASIZE-40, /* leave some space for login */ 734 "SETUP rtsp://%s%s%s/%s RTSP/1.0\r\n" 735 "CSeq: %d\r\n" 736 "Ntrip-Version: Ntrip/2.0\r\n" 737 "Ntrip-Component: Ntripclient\r\n" 738 "User-Agent: %s/%s\r\n" 739 "Transport: RTP/GNSS;unicast;client_port=%u\r\n" 740 "Authorization: Basic ", 741 args.server, proxyserver ? ":" : "", proxyserver ? args.port : "", 742 args.data, cseq++, AGENTSTRING, revisionstr, localport); 743 if(i > MAXDATASIZE-40 || i < 0) /* second check for old glibc */ 744 { 745 fprintf(stderr, "Requested data too long\n"); 746 stop = 1; 747 } 748 i += encode(buf+i, MAXDATASIZE-i-4, args.user, args.password); 749 if(i > MAXDATASIZE-4) 750 { 751 fprintf(stderr, "Username and/or password too long\n"); 752 stop = 1; 753 } 754 buf[i++] = '\r'; 755 buf[i++] = '\n'; 756 buf[i++] = '\r'; 757 buf[i++] = '\n'; 758 if(args.nmea) 759 { 760 int j = snprintf(buf+i, MAXDATASIZE-i, "%s\r\n", args.nmea); 761 if(j >= 0 && j < MAXDATASIZE-i) 762 i += j; 763 else 764 764 { 765 fprintf(stderr, " Could not extract server port\n");766 exit(1);765 fprintf(stderr, "NMEA string too long\n"); 766 stop = 1; 767 767 } 768 768 } 769 l = strlen(sessioncheck)-1; 770 j=0; 771 for(i = 0; j != l && i < numbytes-l; ++i) 772 { 773 for(j = 0; j < l && tolower(buf[i+j]) == sessioncheck[j]; ++j) 774 ; 775 } 776 if(i == numbytes-l) 777 { 778 fprintf(stderr, "No session number found\n"); 779 exit(1); 780 } 781 else 782 { 783 i+=l; 784 while(i < numbytes && buf[i] >= '0' && buf[i] <= '9') 785 session = session * 10 + buf[i++]-'0'; 786 if(buf[i] != '\r') 769 } 770 if(!stop && !error) 771 { 772 if(send(sockfd, buf, (size_t)i, 0) != i) 773 { 774 perror("send"); 775 error = 1; 776 } 777 else if((numbytes=recv(sockfd, buf, MAXDATASIZE-1, 0)) == -1) 778 { 779 perror("recv"); 780 error = 1; 781 } 782 else if(numbytes >= 17 && !strncmp(buf, "RTSP/1.0 200 OK\r\n", 17)) 783 { 784 int serverport = 0, session = 0; 785 const char *portcheck = "server_port="; 786 const char *sessioncheck = "session: "; 787 int l = strlen(portcheck)-1; 788 int j=0; 789 for(i = 0; j != l && i < numbytes-l; ++i) 787 790 { 788 f printf(stderr, "Could not extract session number\n");789 exit(1);791 for(j = 0; j < l && tolower(buf[i+j]) == portcheck[j]; ++j) 792 ; 790 793 } 791 } 792 if(args.initudp) 793 { 794 printf("Sending initial UDP packet\n"); 795 struct sockaddr_in casterRTP; 796 char rtpbuffer[12]; 797 int i; 798 rtpbuffer[0] = (2<<6); 799 /* padding, extension, csrc are empty */ 800 rtpbuffer[1] = 96; 801 /* marker is empty */ 802 rtpbuffer[2] = 0; 803 rtpbuffer[3] = 0; 804 rtpbuffer[4] = 0; 805 rtpbuffer[5] = 0; 806 rtpbuffer[6] = 0; 807 rtpbuffer[7] = 0; 808 /* sequence and timestamp are empty */ 809 rtpbuffer[8] = (session>>24)&0xFF; 810 rtpbuffer[9] = (session>>16)&0xFF; 811 rtpbuffer[10] = (session>>8)&0xFF; 812 rtpbuffer[11] = (session)&0xFF; 813 /* fill structure with caster address information for UDP */ 814 memset(&casterRTP, 0, sizeof(casterRTP)); 815 casterRTP.sin_family = AF_INET; 816 casterRTP.sin_port = htons(serverport); 817 casterRTP.sin_addr = *((struct in_addr *)he->h_addr); 818 819 if((i = sendto(sockudp, rtpbuffer, 12, 0, 820 (struct sockaddr *) &casterRTP, sizeof(casterRTP))) != 12) 821 perror("WARNING: could not send initial UDP packet"); 822 } 823 824 i = snprintf(buf, MAXDATASIZE, 825 "PLAY rtsp://%s%s%s/%s RTSP/1.0\r\n" 826 "CSeq: %d\r\n" 827 "Session: %d\r\n" 828 "\r\n", 829 args.server, proxyserver ? ":" : "", proxyserver ? args.port : "", 830 args.data, cseq++, session); 831 832 if(i > MAXDATASIZE || i < 0) /* second check for old glibc */ 833 { 834 fprintf(stderr, "Requested data too long\n"); 835 exit(1); 836 } 837 if(send(sockfd, buf, (size_t)i, 0) != i) 838 { 839 perror("send"); 840 exit(1); 841 } 842 if((numbytes=recv(sockfd, buf, MAXDATASIZE-1, 0)) != -1) 843 { 844 if(numbytes >= 17 && !strncmp(buf, "RTSP/1.0 200 OK\r\n", 17)) 794 if(i == numbytes-l) 845 795 { 846 struct sockaddr_in addrRTP; 847 /* fill structure with caster address information for UDP */ 848 memset(&addrRTP, 0, sizeof(addrRTP)); 849 addrRTP.sin_family = AF_INET; 850 addrRTP.sin_port = htons(serverport); 851 their_addr.sin_addr = *((struct in_addr *)he->h_addr); 852 len = sizeof(addrRTP); 853 int ts = 0; 854 int sn = 0; 855 int ssrc = 0; 856 int init = 0; 857 int u, v, w; 858 while(!stop && (i = recvfrom(sockudp, buf, 1526, 0, 859 (struct sockaddr*) &addrRTP, &len)) > 0) 796 fprintf(stderr, "No server port number found\n"); 797 stop = 1; 798 } 799 else 800 { 801 i+=l; 802 while(i < numbytes && buf[i] >= '0' && buf[i] <= '9') 803 serverport = serverport * 10 + buf[i++]-'0'; 804 if(buf[i] != '\r' && buf[i] != ';') 860 805 { 861 #ifndef WINDOWSVERSION 862 alarm(ALARMTIME); 863 #endif 864 if(i >= 12+1 && (unsigned char)buf[0] == (2 << 6) && buf[1] == 0x60) 806 fprintf(stderr, "Could not extract server port\n"); 807 stop = 1; 808 } 809 } 810 if(!stop && !error) 811 { 812 l = strlen(sessioncheck)-1; 813 j=0; 814 for(i = 0; j != l && i < numbytes-l; ++i) 815 { 816 for(j = 0; j < l && tolower(buf[i+j]) == sessioncheck[j]; ++j) 817 ; 818 } 819 if(i == numbytes-l) 820 { 821 fprintf(stderr, "No session number found\n"); 822 stop = 1; 823 } 824 else 825 { 826 i+=l; 827 while(i < numbytes && buf[i] >= '0' && buf[i] <= '9') 828 session = session * 10 + buf[i++]-'0'; 829 if(buf[i] != '\r') 865 830 { 866 u= ((unsigned char)buf[2]<<8)+(unsigned char)buf[3]; 867 v = ((unsigned char)buf[4]<<24)+((unsigned char)buf[5]<<16) 868 +((unsigned char)buf[6]<<8)+(unsigned char)buf[7]; 869 w = ((unsigned char)buf[8]<<24)+((unsigned char)buf[9]<<16) 870 +((unsigned char)buf[10]<<8)+(unsigned char)buf[11]; 871 872 if(init) 873 { 874 if(u < -30000 && sn > 30000) sn -= 0xFFFF; 875 if(ssrc != w || ts > v) 876 { 877 fprintf(stderr, "Illegal UDP data received.\n"); 878 exit(1); 879 } 880 if(u > sn) /* don't show out-of-order packets */ 881 fwrite(buf+12, (size_t)i-12, 1, stdout); 882 } 883 sn = u; ts = v; ssrc = w; init = 1; 884 } 885 else 886 { 887 fprintf(stderr, "Illegal UDP header.\n"); 888 exit(1); 831 fprintf(stderr, "Could not extract session number\n"); 832 stop = 1; 889 833 } 890 834 } 891 835 } 892 i = snprintf(buf, MAXDATASIZE, 893 "TEARDOWN rtsp://%s%s%s/%s RTSP/1.0\r\n" 894 "CSeq: %d\r\n" 895 "Session: %d\r\n" 896 "\r\n", 897 args.server, proxyserver ? ":" : "", proxyserver ? args.port : "", 898 args.data, cseq++, session); 899 900 if(i > MAXDATASIZE || i < 0) /* second check for old glibc */ 836 if(!stop && !error && args.initudp) 901 837 { 902 fprintf(stderr, "Requested data too long\n"); 903 exit(1); 838 printf("Sending initial UDP packet\n"); 839 struct sockaddr_in casterRTP; 840 char rtpbuffer[12]; 841 int i; 842 rtpbuffer[0] = (2<<6); 843 /* padding, extension, csrc are empty */ 844 rtpbuffer[1] = 96; 845 /* marker is empty */ 846 rtpbuffer[2] = 0; 847 rtpbuffer[3] = 0; 848 rtpbuffer[4] = 0; 849 rtpbuffer[5] = 0; 850 rtpbuffer[6] = 0; 851 rtpbuffer[7] = 0; 852 /* sequence and timestamp are empty */ 853 rtpbuffer[8] = (session>>24)&0xFF; 854 rtpbuffer[9] = (session>>16)&0xFF; 855 rtpbuffer[10] = (session>>8)&0xFF; 856 rtpbuffer[11] = (session)&0xFF; 857 /* fill structure with caster address information for UDP */ 858 memset(&casterRTP, 0, sizeof(casterRTP)); 859 casterRTP.sin_family = AF_INET; 860 casterRTP.sin_port = htons(serverport); 861 casterRTP.sin_addr = *((struct in_addr *)he->h_addr); 862 863 if((i = sendto(sockudp, rtpbuffer, 12, 0, 864 (struct sockaddr *) &casterRTP, sizeof(casterRTP))) != 12) 865 perror("WARNING: could not send initial UDP packet"); 904 866 } 905 if( send(sockfd, buf, (size_t)i, 0) != i)867 if(!stop && !error) 906 868 { 907 perror("send"); 908 exit(1); 869 i = snprintf(buf, MAXDATASIZE, 870 "PLAY rtsp://%s%s%s/%s RTSP/1.0\r\n" 871 "CSeq: %d\r\n" 872 "Session: %d\r\n" 873 "\r\n", 874 args.server, proxyserver ? ":" : "", proxyserver ? args.port : "", 875 args.data, cseq++, session); 876 877 if(i > MAXDATASIZE || i < 0) /* second check for old glibc */ 878 { 879 fprintf(stderr, "Requested data too long\n"); 880 stop=1; 881 } 882 else if(send(sockfd, buf, (size_t)i, 0) != i) 883 { 884 perror("send"); 885 error = 1; 886 } 887 else if((numbytes=recv(sockfd, buf, MAXDATASIZE-1, 0)) != -1) 888 { 889 if(numbytes >= 17 && !strncmp(buf, "RTSP/1.0 200 OK\r\n", 17)) 890 { 891 struct sockaddr_in addrRTP; 892 /* fill structure with caster address information for UDP */ 893 memset(&addrRTP, 0, sizeof(addrRTP)); 894 addrRTP.sin_family = AF_INET; 895 addrRTP.sin_port = htons(serverport); 896 their_addr.sin_addr = *((struct in_addr *)he->h_addr); 897 len = sizeof(addrRTP); 898 int ts = 0; 899 int sn = 0; 900 int ssrc = 0; 901 int init = 0; 902 int u, v, w; 903 while(!stop && !error && (i = recvfrom(sockudp, buf, 1526, 0, 904 (struct sockaddr*) &addrRTP, &len)) > 0) 905 { 906 #ifndef WINDOWSVERSION 907 alarm(ALARMTIME); 908 #endif 909 if(i >= 12+1 && (unsigned char)buf[0] == (2 << 6) && buf[1] == 0x60) 910 { 911 u= ((unsigned char)buf[2]<<8)+(unsigned char)buf[3]; 912 v = ((unsigned char)buf[4]<<24)+((unsigned char)buf[5]<<16) 913 +((unsigned char)buf[6]<<8)+(unsigned char)buf[7]; 914 w = ((unsigned char)buf[8]<<24)+((unsigned char)buf[9]<<16) 915 +((unsigned char)buf[10]<<8)+(unsigned char)buf[11]; 916 917 if(init) 918 { 919 if(u < -30000 && sn > 30000) sn -= 0xFFFF; 920 if(ssrc != w || ts > v) 921 { 922 fprintf(stderr, "Illegal UDP data received.\n"); 923 continue; 924 } 925 else if(u > sn) /* don't show out-of-order packets */ 926 fwrite(buf+12, (size_t)i-12, 1, stdout); 927 } 928 sn = u; ts = v; ssrc = w; init = 1; 929 } 930 else 931 { 932 fprintf(stderr, "Illegal UDP header.\n"); 933 continue; 934 } 935 } 936 } 937 i = snprintf(buf, MAXDATASIZE, 938 "TEARDOWN rtsp://%s%s%s/%s RTSP/1.0\r\n" 939 "CSeq: %d\r\n" 940 "Session: %d\r\n" 941 "\r\n", 942 args.server, proxyserver ? ":" : "", proxyserver ? args.port : "", 943 args.data, cseq++, session); 944 945 if(i > MAXDATASIZE || i < 0) /* second check for old glibc */ 946 { 947 fprintf(stderr, "Requested data too long\n"); 948 stop = 1; 949 } 950 else if(send(sockfd, buf, (size_t)i, 0) != i) 951 { 952 perror("send"); 953 error = 1; 954 } 955 } 956 else 957 { 958 fprintf(stderr, "Could not start data stream.\n"); 959 error = 1; 960 } 909 961 } 910 962 } 911 963 else 912 964 { 913 fprintf(stderr, "Could not start data stream.\n"); 914 exit(1); 915 } 916 } 917 else 918 { 919 fprintf(stderr, "Could not setup initial control connection.\n"); 920 exit(1); 965 fprintf(stderr, "Could not setup initial control connection.\n"); 966 error = 1; 967 } 968 if(sockudp) 969 closesocket(sockudp); 921 970 } 922 971 } 923 972 else 924 973 { 925 perror("recv"); 926 exit(1); 927 } 928 } 929 else 930 { 931 if(connect(sockfd, (struct sockaddr *)&their_addr, 932 sizeof(struct sockaddr)) == -1) 933 { 934 perror("connect"); 935 exit(1); 936 } 937 if(!args.data) 938 { 939 i = snprintf(buf, MAXDATASIZE, 940 "GET %s%s%s%s/ HTTP/1.0\r\n" 941 "Host: %s\r\n%s" 942 "User-Agent: %s/%s\r\n" 943 "Connection: close\r\n" 944 "\r\n" 945 , proxyserver ? "http://" : "", proxyserver ? proxyserver : "", 946 proxyserver ? ":" : "", proxyserver ? proxyport : "", 947 args.server, args.mode == NTRIP1 ? "" : "Ntrip-Version: Ntrip/2.0\r\n", 948 AGENTSTRING, revisionstr); 949 } 950 else 951 { 952 i=snprintf(buf, MAXDATASIZE-40, /* leave some space for login */ 953 "GET %s%s%s%s/%s HTTP/1.0\r\n" 954 "Host: %s\r\n%s" 955 "User-Agent: %s/%s\r\n" 956 "Connection: close\r\n" 957 "Authorization: Basic " 958 , proxyserver ? "http://" : "", proxyserver ? proxyserver : "", 959 proxyserver ? ":" : "", proxyserver ? proxyport : "", 960 args.data, args.server, 961 args.mode == NTRIP1 ? "" : "Ntrip-Version: Ntrip/2.0\r\n", 962 AGENTSTRING, revisionstr); 963 if(i > MAXDATASIZE-40 || i < 0) /* second check for old glibc */ 974 if(connect(sockfd, (struct sockaddr *)&their_addr, 975 sizeof(struct sockaddr)) == -1) 964 976 { 965 fprintf(stderr, "Requested data too long\n");966 e xit(1);977 perror("connect"); 978 error = 1; 967 979 } 968 i += encode(buf+i, MAXDATASIZE-i-4, args.user, args.password); 969 if(i > MAXDATASIZE-4) 980 if(!stop && !error) 970 981 { 971 fprintf(stderr, "Username and/or password too long\n"); 972 exit(1); 982 if(!args.data) 983 { 984 i = snprintf(buf, MAXDATASIZE, 985 "GET %s%s%s%s/ HTTP/1.0\r\n" 986 "Host: %s\r\n%s" 987 "User-Agent: %s/%s\r\n" 988 "Connection: close\r\n" 989 "\r\n" 990 , proxyserver ? "http://" : "", proxyserver ? proxyserver : "", 991 proxyserver ? ":" : "", proxyserver ? proxyport : "", 992 args.server, args.mode == NTRIP1 ? "" : "Ntrip-Version: Ntrip/2.0\r\n", 993 AGENTSTRING, revisionstr); 994 } 995 else 996 { 997 i=snprintf(buf, MAXDATASIZE-40, /* leave some space for login */ 998 "GET %s%s%s%s/%s HTTP/1.0\r\n" 999 "Host: %s\r\n%s" 1000 "User-Agent: %s/%s\r\n" 1001 "Connection: close\r\n" 1002 "Authorization: Basic " 1003 , proxyserver ? "http://" : "", proxyserver ? proxyserver : "", 1004 proxyserver ? ":" : "", proxyserver ? proxyport : "", 1005 args.data, args.server, 1006 args.mode == NTRIP1 ? "" : "Ntrip-Version: Ntrip/2.0\r\n", 1007 AGENTSTRING, revisionstr); 1008 if(i > MAXDATASIZE-40 || i < 0) /* second check for old glibc */ 1009 { 1010 fprintf(stderr, "Requested data too long\n"); 1011 stop = 1; 1012 } 1013 else 1014 { 1015 i += encode(buf+i, MAXDATASIZE-i-4, args.user, args.password); 1016 if(i > MAXDATASIZE-4) 1017 { 1018 fprintf(stderr, "Username and/or password too long\n"); 1019 stop = 1; 1020 } 1021 else 1022 { 1023 buf[i++] = '\r'; 1024 buf[i++] = '\n'; 1025 buf[i++] = '\r'; 1026 buf[i++] = '\n'; 1027 if(args.nmea) 1028 { 1029 int j = snprintf(buf+i, MAXDATASIZE-i, "%s\r\n", args.nmea); 1030 if(j >= 0 && j < MAXDATASIZE-i) 1031 i += j; 1032 else 1033 { 1034 fprintf(stderr, "NMEA string too long\n"); 1035 stop = 1; 1036 } 1037 } 1038 } 1039 } 1040 } 973 1041 } 974 buf[i++] = '\r'; 975 buf[i++] = '\n'; 976 buf[i++] = '\r'; 977 buf[i++] = '\n'; 978 if(args.nmea) 1042 if(!stop && !error) 979 1043 { 980 int j = snprintf(buf+i, MAXDATASIZE-i, "%s\r\n", args.nmea); 981 if(j >= 0 && j < MAXDATASIZE-i) 982 i += j; 983 else 984 { 985 fprintf(stderr, "NMEA string too long\n"); 986 exit(1); 987 } 988 } 989 } 990 if(send(sockfd, buf, (size_t)i, 0) != i) 991 { 992 perror("send"); 993 exit(1); 994 } 995 if(args.data && *args.data != '%') 996 { 997 int k = 0; 998 int chunkymode = 0; 999 int starttime = time(0); 1000 int lastout = starttime; 1001 int totalbytes = 0; 1002 int chunksize = 0; 1003 1004 while(!stop && (numbytes=recv(sockfd, buf, MAXDATASIZE-1, 0)) > 0) 1005 { 1044 if(send(sockfd, buf, (size_t)i, 0) != i) 1045 { 1046 perror("send"); 1047 error = 1; 1048 } 1049 else if(args.data && *args.data != '%') 1050 { 1051 int k = 0; 1052 int chunkymode = 0; 1053 int starttime = time(0); 1054 int lastout = starttime; 1055 int totalbytes = 0; 1056 int chunksize = 0; 1057 1058 while(!stop && !error && 1059 (numbytes=recv(sockfd, buf, MAXDATASIZE-1, 0)) > 0) 1060 { 1006 1061 #ifndef WINDOWSVERSION 1007 alarm(ALARMTIME);1062 alarm(ALARMTIME); 1008 1063 #endif 1009 if(!k) 1010 { 1011 if( numbytes > 17 && 1012 !strstr(buf, "ICY 200 OK") && /* case 'proxy & ntrip 1.0 caster' */ 1013 (!strncmp(buf, "HTTP/1.1 200 OK\r\n", 17) || 1014 !strncmp(buf, "HTTP/1.0 200 OK\r\n", 17)) ) 1015 { 1016 const char *datacheck = "Content-Type: gnss/data\r\n"; 1017 const char *chunkycheck = "Transfer-Encoding: chunked\r\n"; 1018 int l = strlen(datacheck)-1; 1019 int j=0; 1020 for(i = 0; j != l && i < numbytes-l; ++i) 1064 if(!k) 1021 1065 { 1022 for(j = 0; j < l && buf[i+j] == datacheck[j]; ++j) 1023 ; 1066 if( numbytes > 17 && 1067 !strstr(buf, "ICY 200 OK") && /* case 'proxy & ntrip 1.0 caster' */ 1068 (!strncmp(buf, "HTTP/1.1 200 OK\r\n", 17) || 1069 !strncmp(buf, "HTTP/1.0 200 OK\r\n", 17)) ) 1070 { 1071 const char *datacheck = "Content-Type: gnss/data\r\n"; 1072 const char *chunkycheck = "Transfer-Encoding: chunked\r\n"; 1073 int l = strlen(datacheck)-1; 1074 int j=0; 1075 for(i = 0; j != l && i < numbytes-l; ++i) 1076 { 1077 for(j = 0; j < l && buf[i+j] == datacheck[j]; ++j) 1078 ; 1079 } 1080 if(i == numbytes-l) 1081 { 1082 fprintf(stderr, "No 'Content-Type: gnss/data' found\n"); 1083 error = 1; 1084 } 1085 l = strlen(chunkycheck)-1; 1086 j=0; 1087 for(i = 0; j != l && i < numbytes-l; ++i) 1088 { 1089 for(j = 0; j < l && buf[i+j] == chunkycheck[j]; ++j) 1090 ; 1091 } 1092 if(i < numbytes-l) 1093 chunkymode = 1; 1094 } 1095 else if(!strstr(buf, "ICY 200 OK")) 1096 { 1097 fprintf(stderr, "Could not get the requested data: "); 1098 for(k = 0; k < numbytes && buf[k] != '\n' && buf[k] != '\r'; ++k) 1099 { 1100 fprintf(stderr, "%c", isprint(buf[k]) ? buf[k] : '.'); 1101 } 1102 fprintf(stderr, "\n"); 1103 error = 1; 1104 } 1105 else if(args.mode != NTRIP1) 1106 { 1107 fprintf(stderr, "NTRIP version 2 HTTP connection failed%s.\n", 1108 args.mode == AUTO ? ", falling back to NTRIP1" : ""); 1109 if(args.mode == HTTP) 1110 stop = 1; 1111 } 1112 ++k; 1024 1113 } 1025 if(i == numbytes-l)1114 else 1026 1115 { 1027 fprintf(stderr, "No 'Content-Type: gnss/data' found\n"); 1028 exit(1); 1029 } 1030 l = strlen(chunkycheck)-1; 1031 j=0; 1032 for(i = 0; j != l && i < numbytes-l; ++i) 1033 { 1034 for(j = 0; j < l && buf[i+j] == chunkycheck[j]; ++j) 1035 ; 1036 } 1037 if(i < numbytes-l) 1038 chunkymode = 1; 1039 } 1040 else if(!strstr(buf, "ICY 200 OK")) 1041 { 1042 fprintf(stderr, "Could not get the requested data: "); 1043 for(k = 0; k < numbytes && buf[k] != '\n' && buf[k] != '\r'; ++k) 1044 { 1045 fprintf(stderr, "%c", isprint(buf[k]) ? buf[k] : '.'); 1046 } 1047 fprintf(stderr, "\n"); 1048 exit(1); 1049 } 1050 else if(args.mode != NTRIP1) 1051 { 1052 fprintf(stderr, "NTRIP version 2 HTTP connection failed%s.\n", 1053 args.mode == AUTO ? ", falling back to NTRIP1" : ""); 1054 if(args.mode == HTTP) 1055 exit(1); 1056 } 1057 ++k; 1058 } 1059 else 1060 { 1061 sleeptime = 0; 1062 if(chunkymode) 1063 { 1064 int stop = 0; 1065 int pos = 0; 1066 while(!stop && pos < numbytes) 1067 { 1068 switch(chunkymode) 1116 sleeptime = 0; 1117 if(chunkymode) 1069 1118 { 1070 case 1: /* reading number starts */ 1071 chunksize = 0; 1072 ++chunkymode; /* no break */ 1073 case 2: /* during reading number */ 1074 i = buf[pos++]; 1075 if(i >= '0' && i <= '9') chunksize = chunksize*16+i-'0'; 1076 else if(i >= 'a' && i <= 'f') chunksize = chunksize*16+i-'a'+10; 1077 else if(i >= 'A' && i <= 'F') chunksize = chunksize*16+i-'A'+10; 1078 else if(i == '\r') ++chunkymode; 1079 else if(i == ';') chunkymode = 5; 1080 else stop = 1; 1081 break; 1082 case 3: /* scanning for return */ 1083 if(buf[pos++] == '\n') chunkymode = chunksize ? 4 : 1; 1084 else stop = 1; 1085 break; 1086 case 4: /* output data */ 1087 i = numbytes-pos; 1088 if(i > chunksize) i = chunksize; 1119 int cstop = 0; 1120 int pos = 0; 1121 while(!stop && !cstop && !error && pos < numbytes) 1122 { 1123 switch(chunkymode) 1124 { 1125 case 1: /* reading number starts */ 1126 chunksize = 0; 1127 ++chunkymode; /* no break */ 1128 case 2: /* during reading number */ 1129 i = buf[pos++]; 1130 if(i >= '0' && i <= '9') chunksize = chunksize*16+i-'0'; 1131 else if(i >= 'a' && i <= 'f') chunksize = chunksize*16+i-'a'+10; 1132 else if(i >= 'A' && i <= 'F') chunksize = chunksize*16+i-'A'+10; 1133 else if(i == '\r') ++chunkymode; 1134 else if(i == ';') chunkymode = 5; 1135 else cstop = 1; 1136 break; 1137 case 3: /* scanning for return */ 1138 if(buf[pos++] == '\n') chunkymode = chunksize ? 4 : 1; 1139 else cstop = 1; 1140 break; 1141 case 4: /* output data */ 1142 i = numbytes-pos; 1143 if(i > chunksize) i = chunksize; 1144 if(args.serdevice) 1145 { 1146 int ofs = 0; 1147 while(i > ofs && !cstop && !stop && !error) 1148 { 1149 int j = SerialWrite(&sx, buf+pos+ofs, i-ofs); 1150 if(j < 0) 1151 { 1152 fprintf(stderr, "Could not access serial device\n"); 1153 stop = 1; 1154 } 1155 else 1156 ofs += j; 1157 } 1158 } 1159 else 1160 fwrite(buf+pos, (size_t)i, 1, stdout); 1161 totalbytes += i; 1162 chunksize -= i; 1163 pos += i; 1164 if(!chunksize) 1165 chunkymode = 1; 1166 break; 1167 case 5: 1168 if(i == '\r') chunkymode = 3; 1169 break; 1170 } 1171 } 1172 if(cstop) 1173 { 1174 fprintf(stderr, "Error in chunky transfer encoding\n"); 1175 error = 1; 1176 } 1177 } 1178 else 1179 { 1180 totalbytes += numbytes; 1089 1181 if(args.serdevice) 1090 1182 { 1091 1183 int ofs = 0; 1092 while( i> ofs && !stop)1184 while(numbytes > ofs && !stop) 1093 1185 { 1094 int j = SerialWrite(&sx, buf+pos+ofs, i-ofs);1095 if( j< 0)1186 int i = SerialWrite(&sx, buf+ofs, numbytes-ofs); 1187 if(i < 0) 1096 1188 { 1097 1189 fprintf(stderr, "Could not access serial device\n"); … … 1099 1191 } 1100 1192 else 1101 ofs += j;1193 ofs += i; 1102 1194 } 1103 1195 } 1104 1196 else 1105 fwrite(buf+pos, (size_t)i, 1, stdout); 1106 totalbytes += i; 1107 chunksize -= i; 1108 pos += i; 1109 if(!chunksize) 1110 chunkymode = 1; 1111 break; 1112 case 5: 1113 if(i == '\r') chunkymode = 3; 1114 break; 1197 fwrite(buf, (size_t)numbytes, 1, stdout); 1115 1198 } 1116 } 1117 if(stop) 1118 { 1119 fprintf(stderr, "Error in chunky transfer encoding\n"); 1120 break; 1121 } 1122 } 1123 else 1124 { 1125 totalbytes += numbytes; 1126 if(args.serdevice) 1127 { 1128 int ofs = 0; 1129 while(numbytes > ofs && !stop) 1199 fflush(stdout); 1200 if(totalbytes < 0) /* overflow */ 1130 1201 { 1131 int i = SerialWrite(&sx, buf+ofs, numbytes-ofs); 1132 if(i < 0) 1202 totalbytes = 0; 1203 starttime = time(0); 1204 lastout = starttime; 1205 } 1206 if(args.serdevice && !stop) 1207 { 1208 int doloop = 1; 1209 while(doloop && !stop) 1133 1210 { 1134 fprintf(stderr, "Could not access serial device\n"); 1135 stop = 1; 1136 } 1137 else 1138 ofs += i; 1139 } 1140 } 1141 else 1142 fwrite(buf, (size_t)numbytes, 1, stdout); 1143 } 1144 fflush(stdout); 1145 if(totalbytes < 0) /* overflow */ 1146 { 1147 totalbytes = 0; 1148 starttime = time(0); 1149 lastout = starttime; 1150 } 1151 if(args.serdevice && !stop) 1152 { 1153 int doloop = 1; 1154 while(doloop && !stop) 1155 { 1156 int i = SerialRead(&sx, buf, 200); 1157 if(i < 0) 1158 { 1159 fprintf(stderr, "Could not access serial device\n"); 1160 stop = 1; 1161 } 1162 else 1163 { 1164 int j = 0; 1165 if(i < 200) doloop = 0; 1166 fwrite(buf, i, 1, stdout); 1167 while(j < i) 1168 { 1169 if(nmeabufpos < 6) 1211 int i = SerialRead(&sx, buf, 200); 1212 if(i < 0) 1170 1213 { 1171 if(nmeabuffer[nmeabufpos] != buf[j]) 1214 fprintf(stderr, "Could not access serial device\n"); 1215 stop = 1; 1216 } 1217 else 1218 { 1219 int j = 0; 1220 if(i < 200) doloop = 0; 1221 fwrite(buf, i, 1, stdout); 1222 if(ser) 1223 fwrite(buf, i, 1, ser); 1224 while(j < i) 1172 1225 { 1173 if(nmeabufpos) nmeabufpos = 0; 1174 else ++j; 1175 } 1176 else 1177 { 1178 nmeastarpos = 0; 1179 ++j; ++nmeabufpos; 1226 if(nmeabufpos < 6) 1227 { 1228 if(nmeabuffer[nmeabufpos] != buf[j]) 1229 { 1230 if(nmeabufpos) nmeabufpos = 0; 1231 else ++j; 1232 } 1233 else 1234 { 1235 nmeastarpos = 0; 1236 ++j; ++nmeabufpos; 1237 } 1238 } 1239 else if((nmeastarpos && nmeabufpos == nmeastarpos + 3) 1240 || buf[j] == '\r' || buf[j] == '\n') 1241 { 1242 doloop = 0; 1243 nmeabuffer[nmeabufpos++] = '\r'; 1244 nmeabuffer[nmeabufpos++] = '\n'; 1245 if(send(sockfd, nmeabuffer, nmeabufpos, 0) 1246 != (int)nmeabufpos) 1247 { 1248 fprintf(stderr, "Could not send NMEA\n"); 1249 error = 1; 1250 } 1251 nmeabufpos = 0; 1252 } 1253 else if(nmeabufpos > sizeof(nmeabuffer)-10 || 1254 buf[j] == '$') 1255 nmeabufpos = 0; 1256 else 1257 { 1258 if(buf[j] == '*') nmeastarpos = nmeabufpos; 1259 nmeabuffer[nmeabufpos++] = buf[j++]; 1260 } 1180 1261 } 1181 1262 } 1182 else if((nmeastarpos && nmeabufpos == nmeastarpos + 3) 1183 || buf[j] == '\r' || buf[j] == '\n') 1184 { 1185 doloop = 0; 1186 nmeabuffer[nmeabufpos++] = '\r'; 1187 nmeabuffer[nmeabufpos++] = '\n'; 1188 if(send(sockfd, nmeabuffer, nmeabufpos, 0) 1189 != (int)nmeabufpos) 1190 { 1191 fprintf(stderr, "Could not send NMEA\n"); 1192 stop = 1; 1193 } 1194 nmeabufpos = 0; 1195 } 1196 else if(nmeabufpos > sizeof(nmeabuffer)-10 || 1197 buf[j] == '$') 1198 nmeabufpos = 0; 1199 else 1200 { 1201 if(buf[j] == '*') nmeastarpos = nmeabufpos; 1202 nmeabuffer[nmeabufpos++] = buf[j++]; 1203 } 1263 } 1264 } 1265 if(args.bitrate) 1266 { 1267 int t = time(0); 1268 if(t > lastout + 60) 1269 { 1270 lastout = t; 1271 fprintf(stderr, "Bitrate is %dbyte/s (%d seconds accumulated).\n", 1272 totalbytes/(t-starttime), t-starttime); 1204 1273 } 1205 1274 } 1206 1275 } 1207 1276 } 1208 if(args.bitrate) 1277 } 1278 else 1279 { 1280 sleeptime = 0; 1281 while(!stop && (numbytes=recv(sockfd, buf, MAXDATASIZE-1, 0)) > 0) 1209 1282 { 1210 int t = time(0); 1211 if(t > lastout + 60) 1212 { 1213 lastout = t; 1214 fprintf(stderr, "Bitrate is %dbyte/s (%d seconds accumulated).\n", 1215 totalbytes/(t-starttime), t-starttime); 1216 } 1283 #ifndef WINDOWSVERSION 1284 alarm(ALARMTIME); 1285 #endif 1286 fwrite(buf, (size_t)numbytes, 1, stdout); 1217 1287 } 1218 1288 } 1219 1289 } 1220 1290 } 1221 else 1222 { 1223 sleeptime = 0; 1224 while(!stop && (numbytes=recv(sockfd, buf, MAXDATASIZE-1, 0)) > 0) 1225 { 1226 #ifndef WINDOWSVERSION 1227 alarm(ALARMTIME); 1228 #endif 1229 fwrite(buf, (size_t)numbytes, 1, stdout); 1230 } 1231 } 1291 } 1292 if(sockfd) 1232 1293 closesocket(sockfd); 1233 }1234 1294 } while(args.data && *args.data != '%' && !stop); 1235 1295 if(args.serdevice) … … 1237 1297 SerialFree(&sx); 1238 1298 } 1299 if(ser) 1300 fclose(ser); 1239 1301 } 1240 1302 return 0;
Note:
See TracChangeset
for help on using the changeset viewer.