summaryrefslogtreecommitdiff
path: root/noncore/settings/networksettings/ppp/modem.cpp
Unidiff
Diffstat (limited to 'noncore/settings/networksettings/ppp/modem.cpp') (more/less context) (ignore whitespace changes)
-rw-r--r--noncore/settings/networksettings/ppp/modem.cpp6
1 files changed, 4 insertions, 2 deletions
diff --git a/noncore/settings/networksettings/ppp/modem.cpp b/noncore/settings/networksettings/ppp/modem.cpp
index 7b2e2a3..17ada9b 100644
--- a/noncore/settings/networksettings/ppp/modem.cpp
+++ b/noncore/settings/networksettings/ppp/modem.cpp
@@ -579,386 +579,388 @@ QString Modem::parseModemSpeed(const QString &s) {
579int Modem::lockdevice() { 579int Modem::lockdevice() {
580 int fd; 580 int fd;
581 char newlock[80]=""; // safe 581 char newlock[80]=""; // safe
582 582
583 if(!_pppdata->modemLockFile()) { 583 if(!_pppdata->modemLockFile()) {
584 odebug << "The user doesn't want a lockfile." << oendl; 584 odebug << "The user doesn't want a lockfile." << oendl;
585 return 0; 585 return 0;
586 } 586 }
587 587
588 if (modem_is_locked) 588 if (modem_is_locked)
589 return 1; 589 return 1;
590 590
591 QString lockfile = LOCK_DIR"/LCK.."; 591 QString lockfile = LOCK_DIR"/LCK..";
592 lockfile += _pppdata->modemDevice().mid(5); // append everything after /dev/ 592 lockfile += _pppdata->modemDevice().mid(5); // append everything after /dev/
593 593
594 if(access(QFile::encodeName(lockfile), F_OK) == 0) { 594 if(access(QFile::encodeName(lockfile), F_OK) == 0) {
595// if ((fd = Requester::rq-> 595// if ((fd = Requester::rq->
596if ((fd = openLockfile(QFile::encodeName(lockfile), O_RDONLY)) >= 0) { 596if ((fd = openLockfile(QFile::encodeName(lockfile), O_RDONLY)) >= 0) {
597 // Mario: it's not necessary to read more than lets say 32 bytes. If 597 // Mario: it's not necessary to read more than lets say 32 bytes. If
598 // file has more than 32 bytes, skip the rest 598 // file has more than 32 bytes, skip the rest
599 char oldlock[33]; // safe 599 char oldlock[33]; // safe
600 int sz = read(fd, &oldlock, 32); 600 int sz = read(fd, &oldlock, 32);
601 close (fd); 601 close (fd);
602 if (sz <= 0) 602 if (sz <= 0)
603 return 1; 603 return 1;
604 oldlock[sz] = '\0'; 604 oldlock[sz] = '\0';
605 605
606 odebug << "Device is locked by: " << oldlock << "" << oendl; 606 odebug << "Device is locked by: " << oldlock << "" << oendl;
607 607
608 int oldpid; 608 int oldpid;
609 int match = sscanf(oldlock, "%d", &oldpid); 609 int match = sscanf(oldlock, "%d", &oldpid);
610 610
611 // found a pid in lockfile ? 611 // found a pid in lockfile ?
612 if (match < 1 || oldpid <= 0) 612 if (match < 1 || oldpid <= 0)
613 return 1; 613 return 1;
614 614
615 // check if process exists 615 // check if process exists
616 if (kill((pid_t)oldpid, 0) == 0 || errno != ESRCH) 616 if (kill((pid_t)oldpid, 0) == 0 || errno != ESRCH)
617 return 1; 617 return 1;
618 618
619 odebug << "lockfile is stale" << oendl; 619 odebug << "lockfile is stale" << oendl;
620 } 620 }
621 } 621 }
622 622
623 fd = openLockfile(_pppdata->modemDevice(),O_WRONLY|O_TRUNC|O_CREAT); 623 fd = openLockfile(_pppdata->modemDevice(),O_WRONLY|O_TRUNC|O_CREAT);
624 if(fd >= 0) { 624 if(fd >= 0) {
625 sprintf(newlock,"%010d\n", getpid()); 625 sprintf(newlock,"%010d\n", getpid());
626 odebug << "Locking Device: " << newlock << "" << oendl; 626 odebug << "Locking Device: " << newlock << "" << oendl;
627 627
628 write(fd, newlock, strlen(newlock)); 628 write(fd, newlock, strlen(newlock));
629 close(fd); 629 close(fd);
630 modem_is_locked=true; 630 modem_is_locked=true;
631 631
632 return 0; 632 return 0;
633 } 633 }
634 634
635 return -1; 635 return -1;
636 636
637} 637}
638 638
639 639
640// UnLock modem device 640// UnLock modem device
641void Modem::unlockdevice() { 641void Modem::unlockdevice() {
642 if (modem_is_locked) { 642 if (modem_is_locked) {
643 odebug << "UnLocking Modem Device" << oendl; 643 odebug << "UnLocking Modem Device" << oendl;
644 close(modemfd); 644 close(modemfd);
645 modemfd = -1; 645 modemfd = -1;
646 unlink(lockfile); 646 unlink(lockfile);
647 lockfile[0] = '\0'; 647 lockfile[0] = '\0';
648 modem_is_locked=false; 648 modem_is_locked=false;
649 } 649 }
650} 650}
651 651
652int Modem::openLockfile( QString lockfile, int flags) 652int Modem::openLockfile( QString lockfile, int flags)
653{ 653{
654 int fd; 654 int fd;
655 int mode; 655 int mode;
656 flags = O_RDONLY; 656 flags = O_RDONLY;
657 if(flags == O_WRONLY|O_TRUNC|O_CREAT) 657 if(flags == O_WRONLY|O_TRUNC|O_CREAT)
658 mode = 0644; 658 mode = 0644;
659 else 659 else
660 mode = 0; 660 mode = 0;
661 661
662 lockfile = LOCK_DIR; 662 lockfile = LOCK_DIR;
663 lockfile += "/LCK.."; 663 lockfile += "/LCK..";
664 lockfile += device.right( device.length() - device.findRev("/") -1 ); 664 lockfile += device.right( device.length() - device.findRev("/") -1 );
665 odebug << "lockfile >" << lockfile.latin1() << "<" << oendl; 665 odebug << "lockfile >" << lockfile.latin1() << "<" << oendl;
666 // TODO: 666 // TODO:
667 // struct stat st; 667 // struct stat st;
668 // if(stat(lockfile.data(), &st) == -1) { 668 // if(stat(lockfile.data(), &st) == -1) {
669 // if(errno == EBADF) 669 // if(errno == EBADF)
670 // return -1; 670 // return -1;
671 // } else { 671 // } else {
672 // // make sure that this is a regular file 672 // // make sure that this is a regular file
673 // if(!S_ISREG(st.st_mode)) 673 // if(!S_ISREG(st.st_mode))
674 // return -1; 674 // return -1;
675 // } 675 // }
676 if ((fd = open(lockfile, flags, mode)) == -1) { 676 if ((fd = open(lockfile, flags, mode)) == -1) {
677 odebug << "error opening lockfile!" << oendl; 677 odebug << "error opening lockfile!" << oendl;
678 lockfile = QString::null; 678 lockfile = QString::null;
679 fd = open(DEVNULL, O_RDONLY); 679 fd = open(DEVNULL, O_RDONLY);
680 } else 680 } else
681 fchown(fd, 0, 0); 681 fchown(fd, 0, 0);
682 return fd; 682 return fd;
683} 683}
684 684
685 685
686 686
687void alarm_handler(int) { 687void alarm_handler(int) {
688 // fprintf(stderr, "alarm_handler(): Received SIGALRM\n"); 688 // fprintf(stderr, "alarm_handler(): Received SIGALRM\n");
689 689
690 // jump 690 // jump
691 siglongjmp(jmp_buffer, 1); 691 siglongjmp(jmp_buffer, 1);
692} 692}
693 693
694 694
695const char* Modem::authFile(Auth method, int version) { 695const char* Modem::authFile(Auth method, int version) {
696 switch(method|version) { 696 switch(method|version) {
697 case PAP|Original: 697 case PAP|Original:
698 return PAP_AUTH_FILE; 698 return PAP_AUTH_FILE;
699 break; 699 break;
700 case PAP|New: 700 case PAP|New:
701 return PAP_AUTH_FILE".new"; 701 return PAP_AUTH_FILE".new";
702 break; 702 break;
703 case PAP|Old: 703 case PAP|Old:
704 return PAP_AUTH_FILE".old"; 704 return PAP_AUTH_FILE".old";
705 break; 705 break;
706 case CHAP|Original: 706 case CHAP|Original:
707 return CHAP_AUTH_FILE; 707 return CHAP_AUTH_FILE;
708 break; 708 break;
709 case CHAP|New: 709 case CHAP|New:
710 return CHAP_AUTH_FILE".new"; 710 return CHAP_AUTH_FILE".new";
711 break; 711 break;
712 case CHAP|Old: 712 case CHAP|Old:
713 return CHAP_AUTH_FILE".old"; 713 return CHAP_AUTH_FILE".old";
714 break; 714 break;
715 default: 715 default:
716 return 0L; 716 return 0L;
717 } 717 }
718} 718}
719 719
720 720
721bool Modem::createAuthFile(Auth method, const char *username, const char *password) { 721bool Modem::createAuthFile(Auth method, const char *username, const char *password) {
722 const char *authfile, *oldName, *newName; 722 const char *authfile, *oldName, *newName;
723 char line[100]; 723 char line[100];
724 char regexp[2*MaxStrLen+30]; 724 char regexp[2*MaxStrLen+30];
725 regex_t preg; 725 regex_t preg;
726 726
727 if(!(authfile = authFile(method))) 727 if(!(authfile = authFile(method)))
728 return false; 728 return false;
729 729
730 if(!(newName = authFile(method, New))) 730 if(!(newName = authFile(method, New)))
731 return false; 731 return false;
732 732
733 // look for username, "username" or 'username' 733 // look for username, "username" or 'username'
734 // if you modify this RE you have to adapt regexp's size above 734 // if you modify this RE you have to adapt regexp's size above
735 snprintf(regexp, sizeof(regexp), "^[ \t]*%s[ \t]\\|^[ \t]*[\"\']%s[\"\']", 735 snprintf(regexp, sizeof(regexp), "^[ \t]*%s[ \t]\\|^[ \t]*[\"\']%s[\"\']",
736 username,username); 736 username,username);
737 MY_ASSERT(regcomp(&preg, regexp, 0) == 0); 737 MY_ASSERT(regcomp(&preg, regexp, 0) == 0);
738 738
739 // copy to new file pap- or chap-secrets 739 // copy to new file pap- or chap-secrets
740 int old_umask = umask(0077); 740 int old_umask = umask(0077);
741 FILE *fout = fopen(newName, "w"); 741 FILE *fout = fopen(newName, "w");
742 if(fout) { 742 if(fout) {
743 // copy old file 743 // copy old file
744 FILE *fin = fopen(authfile, "r"); 744 FILE *fin = fopen(authfile, "r");
745 if(fin) { 745 if(fin) {
746 while(fgets(line, sizeof(line), fin)) { 746 while(fgets(line, sizeof(line), fin)) {
747 if(regexec(&preg, line, 0, 0L, 0) == 0) 747 if(regexec(&preg, line, 0, 0L, 0) == 0)
748 continue; 748 continue;
749 fputs(line, fout); 749 fputs(line, fout);
750 } 750 }
751 fclose(fin); 751 fclose(fin);
752 } 752 }
753 753
754 // append user/pass pair 754 // append user/pass pair
755 fprintf(fout, "\"%s\"\t*\t\"%s\"\n", username, password); 755 fprintf(fout, "\"%s\"\t*\t\"%s\"\n", username, password);
756 fclose(fout); 756 fclose(fout);
757 } 757 }
758 758
759 // restore umask 759 // restore umask
760 umask(old_umask); 760 umask(old_umask);
761 761
762 // free memory allocated by regcomp 762 // free memory allocated by regcomp
763 regfree(&preg); 763 regfree(&preg);
764 764
765 if(!(oldName = authFile(method, Old))) 765 if(!(oldName = authFile(method, Old)))
766 return false; 766 return false;
767 767
768 // delete old file if any 768 // delete old file if any
769 unlink(oldName); 769 unlink(oldName);
770 770
771 rename(authfile, oldName); 771 if (rename(authfile, oldName) == -1)
772 rename(newName, authfile); 772 return false;
773 if (rename(newName, authfile) == -1)
774 return false;
773 775
774 return true; 776 return true;
775} 777}
776 778
777 779
778bool Modem::removeAuthFile(Auth method) { 780bool Modem::removeAuthFile(Auth method) {
779 const char *authfile, *oldName; 781 const char *authfile, *oldName;
780 782
781 if(!(authfile = authFile(method))) 783 if(!(authfile = authFile(method)))
782 return false; 784 return false;
783 if(!(oldName = authFile(method, Old))) 785 if(!(oldName = authFile(method, Old)))
784 return false; 786 return false;
785 787
786 if(access(oldName, F_OK) == 0) { 788 if(access(oldName, F_OK) == 0) {
787 unlink(authfile); 789 unlink(authfile);
788 return (rename(oldName, authfile) == 0); 790 return (rename(oldName, authfile) == 0);
789 } else 791 } else
790 return false; 792 return false;
791} 793}
792 794
793 795
794bool Modem::setSecret(int method, const char* name, const char* password) 796bool Modem::setSecret(int method, const char* name, const char* password)
795{ 797{
796 798
797 Auth auth; 799 Auth auth;
798 if(method == AUTH_PAPCHAP) 800 if(method == AUTH_PAPCHAP)
799 return setSecret(AUTH_PAP, name, password) && 801 return setSecret(AUTH_PAP, name, password) &&
800 setSecret(AUTH_CHAP, name, password); 802 setSecret(AUTH_CHAP, name, password);
801 803
802 switch(method) { 804 switch(method) {
803 case AUTH_PAP: 805 case AUTH_PAP:
804 auth = Modem::PAP; 806 auth = Modem::PAP;
805 break; 807 break;
806 case AUTH_CHAP: 808 case AUTH_CHAP:
807 auth = Modem::CHAP; 809 auth = Modem::CHAP;
808 break; 810 break;
809 default: 811 default:
810 return false; 812 return false;
811 } 813 }
812 814
813 return createAuthFile(auth, name, password); 815 return createAuthFile(auth, name, password);
814 816
815} 817}
816 818
817bool Modem::removeSecret(int method) 819bool Modem::removeSecret(int method)
818{ 820{
819 Auth auth; 821 Auth auth;
820 822
821 switch(method) { 823 switch(method) {
822 case AUTH_PAP: 824 case AUTH_PAP:
823 auth = Modem::PAP; 825 auth = Modem::PAP;
824 break; 826 break;
825 case AUTH_CHAP: 827 case AUTH_CHAP:
826 auth = Modem::CHAP; 828 auth = Modem::CHAP;
827 break; 829 break;
828 default: 830 default:
829 return false; 831 return false;
830 } 832 }
831 return removeAuthFile( auth ); 833 return removeAuthFile( auth );
832} 834}
833 835
834int checkForInterface() 836int checkForInterface()
835{ 837{
836// I don't know if Linux needs more initialization to get the ioctl to 838// I don't know if Linux needs more initialization to get the ioctl to
837// work, pppd seems to hint it does. But BSD doesn't, and the following 839// work, pppd seems to hint it does. But BSD doesn't, and the following
838// code should compile. 840// code should compile.
839#if (defined(HAVE_NET_IF_PPP_H) || defined(HAVE_LINUX_IF_PPP_H)) && !defined(__svr4__) 841#if (defined(HAVE_NET_IF_PPP_H) || defined(HAVE_LINUX_IF_PPP_H)) && !defined(__svr4__)
840 int s, ok; 842 int s, ok;
841 struct ifreq ifr; 843 struct ifreq ifr;
842 // extern char *no_ppp_msg; 844 // extern char *no_ppp_msg;
843 845
844 if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0) 846 if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
845 return 1; /* can't tell */ 847 return 1; /* can't tell */
846 848
847 strlcpy(ifr.ifr_name, "ppp0", sizeof (ifr.ifr_name)); 849 strlcpy(ifr.ifr_name, "ppp0", sizeof (ifr.ifr_name));
848 ok = ioctl(s, SIOCGIFFLAGS, (caddr_t) &ifr) >= 0; 850 ok = ioctl(s, SIOCGIFFLAGS, (caddr_t) &ifr) >= 0;
849 close(s); 851 close(s);
850 852
851 if (ok == -1) { 853 if (ok == -1) {
852// This is ifdef'd FreeBSD, because FreeBSD is the only BSD that supports 854// This is ifdef'd FreeBSD, because FreeBSD is the only BSD that supports
853// KLDs, the old LKM interface couldn't handle loading devices 855// KLDs, the old LKM interface couldn't handle loading devices
854// dynamically, and thus can't load ppp support on the fly 856// dynamically, and thus can't load ppp support on the fly
855#ifdef __FreeBSD__ 857#ifdef __FreeBSD__
856 // If we failed to load ppp support and don't have it already. 858 // If we failed to load ppp support and don't have it already.
857 if (kldload("if_ppp") == -1) { 859 if (kldload("if_ppp") == -1) {
858 return -1; 860 return -1;
859 } 861 }
860 return 0; 862 return 0;
861#else 863#else
862 return -1; 864 return -1;
863#endif 865#endif
864 } 866 }
865 return 0; 867 return 0;
866#else 868#else
867// We attempt to use the SunOS/SysVr4 method and stat /dev/ppp 869// We attempt to use the SunOS/SysVr4 method and stat /dev/ppp
868 struct stat buf; 870 struct stat buf;
869 871
870 memset(&buf, 0, sizeof(buf)); 872 memset(&buf, 0, sizeof(buf));
871 return stat("/dev/ppp", &buf); 873 return stat("/dev/ppp", &buf);
872#endif 874#endif
873} 875}
874 876
875bool Modem::execpppd(const char *arguments) { 877bool Modem::execpppd(const char *arguments) {
876 char buf[MAX_CMDLEN]; 878 char buf[MAX_CMDLEN];
877 char *args[MaxArgs]; 879 char *args[MaxArgs];
878 pid_t pgrpid; 880 pid_t pgrpid;
879 881
880 if(modemfd<0) 882 if(modemfd<0)
881 return false; 883 return false;
882 884
883 _pppdExitStatus = -1; 885 _pppdExitStatus = -1;
884 886
885 (void)::pipe( m_pppdLOG ); 887 (void)::pipe( m_pppdLOG );
886 888
887 switch(pppdPid = fork()) 889 switch(pppdPid = fork())
888 { 890 {
889 case -1: 891 case -1:
890 fprintf(stderr,"In parent: fork() failed\n"); 892 fprintf(stderr,"In parent: fork() failed\n");
891 ::close( m_pppdLOG[0] ); 893 ::close( m_pppdLOG[0] );
892 ::close( m_pppdLOG[1] ); 894 ::close( m_pppdLOG[1] );
893 return false; 895 return false;
894 break; 896 break;
895 897
896 case 0: 898 case 0:
897 // let's parse the arguments the user supplied into UNIX suitable form 899 // let's parse the arguments the user supplied into UNIX suitable form
898 // that is a list of pointers each pointing to exactly one word 900 // that is a list of pointers each pointing to exactly one word
899 strlcpy(buf, arguments); 901 strlcpy(buf, arguments);
900 parseargs(buf, args); 902 parseargs(buf, args);
901 // become a session leader and let /dev/ttySx 903 // become a session leader and let /dev/ttySx
902 // be the controlling terminal. 904 // be the controlling terminal.
903 pgrpid = setsid(); 905 pgrpid = setsid();
904#ifdef TIOCSCTTY 906#ifdef TIOCSCTTY
905 if(ioctl(modemfd, TIOCSCTTY, 0)<0) 907 if(ioctl(modemfd, TIOCSCTTY, 0)<0)
906 fprintf(stderr, "ioctl() failed.\n"); 908 fprintf(stderr, "ioctl() failed.\n");
907#elif defined (TIOCSPGRP) 909#elif defined (TIOCSPGRP)
908 if(ioctl(modemfd, TIOCSPGRP, &pgrpid)<0) 910 if(ioctl(modemfd, TIOCSPGRP, &pgrpid)<0)
909 fprintf(stderr, "ioctl() failed.\n"); 911 fprintf(stderr, "ioctl() failed.\n");
910#endif 912#endif
911 if(tcsetpgrp(modemfd, pgrpid)<0) 913 if(tcsetpgrp(modemfd, pgrpid)<0)
912 fprintf(stderr, "tcsetpgrp() failed.\n"); 914 fprintf(stderr, "tcsetpgrp() failed.\n");
913 915
914 ::close( m_pppdLOG[0] ); 916 ::close( m_pppdLOG[0] );
915 ::setenv( "LANG", "C", 1 ); // overwrite 917 ::setenv( "LANG", "C", 1 ); // overwrite
916 dup2(m_pppdLOG[1], 11 ); // for logfd 11 918 dup2(m_pppdLOG[1], 11 ); // for logfd 11
917 dup2(modemfd, 0); 919 dup2(modemfd, 0);
918 dup2(modemfd, 1); 920 dup2(modemfd, 1);
919 921
920 922
921 switch (checkForInterface()) { 923 switch (checkForInterface()) {
922 case 1: 924 case 1:
923 fprintf(stderr, "Cannot determine if kernel supports ppp.\n"); 925 fprintf(stderr, "Cannot determine if kernel supports ppp.\n");
924 break; 926 break;
925 case -1: 927 case -1:
926 fprintf(stderr, "Kernel does not support ppp, oops.\n"); 928 fprintf(stderr, "Kernel does not support ppp, oops.\n");
927 break; 929 break;
928 case 0: 930 case 0:
929 fprintf(stderr, "Kernel supports ppp alright.\n"); 931 fprintf(stderr, "Kernel supports ppp alright.\n");
930 break; 932 break;
931 } 933 }
932 934
933 execve(pppdPath(), args, 0L); 935 execve(pppdPath(), args, 0L);
934 _exit(0); 936 _exit(0);
935 break; 937 break;
936 938
937 default: 939 default:
938 odebug << "In parent: pppd pid " << pppdPid << "\n" << oendl; 940 odebug << "In parent: pppd pid " << pppdPid << "\n" << oendl;
939 close(modemfd); 941 close(modemfd);
940 942
941 ::close( m_pppdLOG[1] ); 943 ::close( m_pppdLOG[1] );
942 // set it to nonblocking io 944 // set it to nonblocking io
943 int flag = ::fcntl( m_pppdLOG[0], F_GETFL ); 945 int flag = ::fcntl( m_pppdLOG[0], F_GETFL );
944 946
945 if ( !(flag & O_NONBLOCK) ) { 947 if ( !(flag & O_NONBLOCK) ) {
946 odebug << "Setting nonblocking io" << oendl; 948 odebug << "Setting nonblocking io" << oendl;
947 flag |= O_NONBLOCK; 949 flag |= O_NONBLOCK;
948 ::fcntl(m_pppdLOG[0], F_SETFL, flag ); 950 ::fcntl(m_pppdLOG[0], F_SETFL, flag );
949 } 951 }
950 952
951 delete m_modemDebug; 953 delete m_modemDebug;
952 m_modemDebug = new QSocketNotifier(m_pppdLOG[0], QSocketNotifier::Read, this ); 954 m_modemDebug = new QSocketNotifier(m_pppdLOG[0], QSocketNotifier::Read, this );
953 connect(m_modemDebug, SIGNAL(activated(int) ), 955 connect(m_modemDebug, SIGNAL(activated(int) ),
954 this, SLOT(slotModemDebug(int) ) ); 956 this, SLOT(slotModemDebug(int) ) );
955 957
956 modemfd = -1; 958 modemfd = -1;
957 m_pppdDev = QString::fromLatin1("ppp0"); 959 m_pppdDev = QString::fromLatin1("ppp0");
958 return true; 960 return true;
959 break; 961 break;
960 } 962 }
961} 963}
962 964
963 965
964bool Modem::killpppd() { 966bool Modem::killpppd() {