zoukankan      html  css  js  c++  java
  • telnet客户端程序

    #include <stdio.h>
    #include <stdlib.h>
    #include <unistd.h>
    #include <sys/types.h>
    #include <sys/socket.h>
    #include <netinet/in.h>
    #include <arpa/inet.h>
    #include <termios.h>
    #include <string.h>
    
    #define DO 0xfd
    #define WONT 0xfc
    #define WILL 0xfb
    #define DONT 0xfe
    #define CMD 0xff
    #define CMD_ECHO 1
    #define CMD_WINDOW_SIZE 31
    #define IAC 255
    #define SB 250
    #define SE 240
    #define BUFLEN 200
    #define ESCAPE 27
    
    #define SA struct sockaddr
    
    static struct termios tin;
    static void terminal_set(void);
    static void terminal_reset(void);
    void negotiate(int sock, unsigned char *buf, int len);
    void connect_to_server(int sock, int port, char *address);
    
    int main(int argc, char *argv[]) {
        int sock;
        unsigned char buf[BUFLEN + 1];
        int len;
        int i;
        int port = 23;
     
        if (argc < 2 || argc > 3) {
            printf("Usage: %s address [port]
    ", argv[0]);
            return 1;
        }
        
        if (argc == 3)
            port = atoi(argv[2]);
     
        // Create socket
        sock = socket(AF_INET, SOCK_STREAM, 0);
        if (sock == -1) {
            perror("Could not create socket. Error");
            return 1;
        }
        printf("Trying %s...
    ", argv[1]);
     
        connect_to_server(sock, port, argv[1]);
     
        printf("Connected to %s
    ", argv[1]);
        puts("Escape character is '^]'.");
     
        // set terminal
        terminal_set();
        atexit(terminal_reset);
     
        // 1 second
        struct timeval ts;
        ts.tv_sec = 1;
        ts.tv_usec = 0;
     
        while (1) {
            // select setup
            fd_set fds;
            FD_ZERO(&fds);
            if (sock != 0)
                FD_SET(sock, &fds);
            FD_SET(0, &fds);
     
            // wait for data
            int nready = select(sock + 1, &fds, (fd_set *) 0, (fd_set *) 0, &ts);
            if (nready < 0) {
                perror("select. Error");
                return 1;
            } else if (nready == 0) {
                ts.tv_sec = 1;
                ts.tv_usec = 0;
            } else if (sock != 0 && FD_ISSET(sock, &fds)) {
                // start by reading a single byte
                int rv;
                if ((rv = recv(sock, buf, 1, 0)) < 0)
                    return 1;
                else if (rv == 0) {
                    printf("Connection closed by the remote end
    
    ");
                    return 0;
                }
     
                if (buf[0] == CMD) {
                    // read 2 more bytes
                    len = recv(sock, buf + 1, 2, 0);
                    if (len < 0)
                        return 1;
                    else if (len == 0) {
                        printf("Connection closed by the remote end
    
    ");
                        return 0;
                    }
                    negotiate(sock, buf, 3);
                } else {
                    len = 1;
                    buf[len] = '';
                    printf("%s", buf);
                    fflush(stdout);
                }
            }
     
            else if (FD_ISSET(0, &fds)) {
                static char crlf[] = { '
    ', '
    ' };
                buf[0] = getc(stdin); //fgets(buf, 1, stdin);
                if (buf[0] == '
    ') { // with the terminal in raw mode we need to force a LF
                    if (send(sock, crlf, 1, 0) < 0) {
                        return 1;
                    }
                } else if (buf[0] == ESCAPE) {
                    printf("Connection closed by the client end
    
    ");
                    return 0;
                } else {
                    if (send(sock, buf, 1, 0) < 0)
                        return 1;
                }
            }
        }
        close(sock);
        return 0;
    }
    
    void negotiate(int sock, unsigned char *buf, int len) {
        int i;
        const char* option_code[350];
        option_code[00] = "TRANSMIT-BINARY";
        option_code[01] = "ECHO";
        option_code[03] = "SUPPRESS-GO-AHEAD";
        option_code[05] = "STATUS";
        option_code[06] = "TIMING-MARK";
        option_code[10] = "NAOCRD";
        option_code[11] = "NAOHTS";
        option_code[12] = "NAOHTD";
        option_code[13] = "NAOFFD";
        option_code[14] = "NAOVTS";
        option_code[15] = "NAOVTD";
        option_code[16] = "NAOLFD";
        option_code[17] = "EXTEND-ASCII";
        option_code[18] = "LOGOUT";
        option_code[19] = "BM";
        option_code[20] = "DET";
        option_code[23] = "SEND-LOCATION";
        option_code[24] = "TERMINAL-TYPE";
        option_code[25] = "END-OF-RECORD";
        option_code[26] = "TUID";
        option_code[27] = "OUTMRK";
        option_code[28] = "TTYLOC";
        option_code[29] = "3270-REGIME";
        option_code[30] = "X.3-PAD";
        option_code[31] = "NAWS";
        option_code[32] = "TERMINAL-SPEED";
        option_code[33] = "TOGGLE-FLOW-CONTROL";
        option_code[34] = "LINEMODE";
        option_code[35] = "X-DISPLAY-LOCATION";
        option_code[36] = "ENVIRON";
        option_code[37] = "AUTHENTICATION";
        option_code[38] = "ENCRYPT";
        option_code[39] = "NEW-ENVIRON";
        option_code[40] = "TN3270E";
        option_code[42] = "CHARSET";
        option_code[44] = "COM-PORT-OPTION";
        option_code[47] = "KERMIT";
        option_code[250] = "SB";
        option_code[240] = "SE";
        option_code[251] = "WILL";
        option_code[252] = "WONT";
        option_code[253] = "DO";
        option_code[254] = "DONT";
        option_code[255] = "IAC";
        if (buf[1] == DO && buf[2] == CMD_WINDOW_SIZE) {
            unsigned char tmp1[10] = { IAC, WILL, CMD_WINDOW_SIZE };
            if (send(sock, tmp1, 3, 0) < 0)
                exit(1);
     
            unsigned char tmp2[10] = { IAC, SB, CMD_WINDOW_SIZE, 0, 80, 0, 24, IAC,
            SE };
            if (send(sock, tmp2, 9, 0) < 0)
                exit(1);
            return;
        }
     
        for (i = 1; i < len; i++) {
            if (buf[i] == DO) {
                buf[i] = WONT;
            } else if (buf[i] == WILL) {
                buf[i] = DO;
            }
        }
     
        if (send(sock, buf, len, 0) < 0)
            exit(1);
    }
     
    static void terminal_set(void) {
        // save terminal configuration
        tcgetattr(STDIN_FILENO, &tin);
     
        static struct termios tlocal;
        memcpy(&tlocal, &tin, sizeof(tin));
        // The file descriptor which has to be turned to raw mode is the standard
        // input of the parent process
        cfmakeraw(&tlocal);
        tcsetattr(STDIN_FILENO, TCSANOW, &tlocal);
    }
     
    static void terminal_reset(void) {
        // restore terminal upon exit
        tcsetattr(STDIN_FILENO, TCSANOW, &tin);
    }
     
    void connect_to_server(int sock, int port, char* address) {
        struct sockaddr_in server;
        server.sin_addr.s_addr = inet_addr(address);
        server.sin_family = AF_INET;
        server.sin_port = htons(port);
     
        //Connect to remote server
        if (connect(sock, (SA *) &server, sizeof(server)) < 0) {
            perror("connect failed. Error
    ");
            exit(1);
        }
    } 
  • 相关阅读:
    线性时不变系统的频率选择滤波器
    Why Programmmers dont have a High Social Status?
    Oracle 的DBA考证
    基于matlab的FIR加窗滤波器设计
    奥本海姆《离散时间信号处理》第二版书评
    Altium Designer 发现的机密——摘自CRAZY BINGO
    sql server 2008 添加登录名
    Silverlight listbox横向排列
    IOS 摄像头使用(1)UIImagePickerController
    ios 如何获得系统时间和日期
  • 原文地址:https://www.cnblogs.com/soldierback/p/10684533.html
Copyright © 2011-2022 走看看