1

なんらかの理由で毎晩午前2時から午前6時頃に死んでしまうようなc++コードがあります。ログファイルを調べたところ、データベースエラーが原因ではないことがわかりました。例外もありません。私はsyslogをチェックしましたが、c++からは何もありません。私はUbuntuサーバーを使用してc++を実行しています。ここにコードを追加しています。これを手伝ってください。

int main(int argc, char *argv[]) {
    try {
        int sockfd, portno, net_socket2, portno2;
        struct sockaddr_in serv_addr;
        struct sockaddr_in si_output2;
        struct hostent *server;
        int iof;

        int n, udp_size;

        unsigned char receivedMessage[256];
        unsigned char buffer[50];

        // register the signal (exception) handler
        signal(SIGINT, SIGINThandler);

        // Log on //////////////////////////////////////////////////////////////////////////////////////////////////////
        printf("Logging on\n");
        log("Logging on");
        portno = SERVER_PORT;
        sockfd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
        if (sockfd < 0) {
            log("ERROR opening socket");
            error("ERROR opening socket");
        }
        printf("Socket opened \n");
        log("Socket opened");
        bzero((char *) &serv_addr, sizeof (serv_addr)); //clear the structure
        serv_addr.sin_family = AF_INET;
        if (inet_aton(SERVER_IP, &serv_addr.sin_addr) == 0) {
            printf("inet_aton() failed \n");
            log("inet_aton() failed ");
            return 0;
        }

        serv_addr.sin_port = htons(portno); //set the host port
        const struct sockaddr *to_cast = (struct sockaddr *) &serv_addr;
        printf("Connecting to %s %d on port %d \n", SERVER_IP, serv_addr.sin_addr.s_addr, portno);
        log("Connecting to port on the server");
        if (connect(sockfd, to_cast, sizeof (serv_addr)) < 0) {
            log("Error connecting");
            error("ERROR connecting\n");
        }

        if ((fcntl(sockfd, F_GETFL, 0)) != -1)
            fcntl(sockfd, F_SETFL, iof | O_NONBLOCK);
        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////

        // now open udp socket to receive messages from host /////////////////////////////////////////////////////////////
        int MESSAGE_PORT = 6001;
        if ((net_socket2 = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) == -1) {
            log("Message socket problem");
            perror("setsockopt");
            exit(1);
            printf("message socket problem \n");
            close(net_socket2);
            return 0;
        }
        memset((char*) &si_output2, sizeof (si_output2), 0);
        si_output2.sin_family = AF_INET;
        si_output2.sin_port = htons(MESSAGE_PORT);
        si_output2.sin_addr.s_addr = INADDR_ANY;

        //bind socket for incomming messages
        log("bind socket for incomming messages");
        if (bind(net_socket2, (struct sockaddr *) &si_output2, sizeof (struct sockaddr)) == -1) {
            log("Socket 2 bind failed");
            printf("socket 2 bind failed \n");
            close(net_socket2);
            return 0;
        }
        //set to non blocking
        if ((iof = fcntl(net_socket2, F_GETFL, 0)) != -1)
            fcntl(net_socket2, F_SETFL, iof | O_NONBLOCK);

        //In the above INADDR_ANY means the message could come from anywhere, you
        //would have to select a free port for MESSAGE_PORT
        ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////

        // Send the logon message
        log("Send the logon message");
        unsigned char* logonMessage = msgLogon();
        //cout << "\nLogon Message Begin: ";
        displayByteArray(logonMessage, 38);
        //cout << "\nLogon Message End\n";
        n = write(sockfd, logonMessage, 38);
        if (n < 0) {
            log("ERROR writing to socket");
            error("ERROR writing to socket");
        }
        // Assume we are logged in now so start receiving messages ////////////////////////////////////////////////////////
        log("Assume we are logged in now so start receiving messages");
        while (true) {
            // Check for incomming message from etsl //
            bzero(receivedMessage, 256); //clear the received message
            n = read(sockfd, receivedMessage, 255);
            if (n > 0) {

                //cout << "\nReceived Message Begin: ";
                //displayByteArray(receivedMessage, n);
                //cout << "\nReceived Message End\n";

                MsgReply message = MsgReply(receivedMessage, n);

                messageHandler(message);

                if (message.getValue()) { //If we can get a reply message

                    unsigned char* replyMessage = message.getReplyMessage();

                    //int m = sizeof(replyMessage)/sizeof(replyMessage[0]);
                    int m = message.getReplyMessageLength();
                    //cout << "\nReply Message Length: m: " << m;
                    n = write(sockfd, replyMessage, m);
                    if (n < 0) {
                        log("ERROR writing to socket");
                        error("ERROR writing to socket");
                    }

                } else {
                    log("Did not reply to this message");
                    //cout << "\nDid not reply to this message\n";
                }
            }

            if (sendLogoff) {
                //cout << "\nreceived a control c";
                log("Send the logoff message");
                // Send the logon message
                unsigned char* logoffMessage = msgLogoff();
                //cout << "\nLogoff Message Begin: ";
                displayByteArray(logoffMessage, 38);
                //cout << "\nLogoff Message End\n";
                n = write(sockfd, logonMessage, 38);
                if (n < 0) {
                    log("ERROR writing to socket");
                    error("ERROR writing to socket");
                }
                sendLogoff = false;
            }           
        }


        log("Exit main block on success");
        return EXIT_SUCCESS;
    } catch (const std::exception& ex) {
        //cout<< ex.what();    
        log(ex.what());
    } catch (const std::string& ex) {
        //cout << ex;
        log(ex);
    } catch (...) {
        log("unknown exception");
    }
}

これがMessageHandlerコードです

void messageHandler(MsgReply& message) {

string msgStr = byteArrayToHexString(message.getReceivedMessage(), 2 * message.getReceivedMessageLength());

int type = messageType(msgStr);

if ((type == 220) || (type == 221)) {

    string subMsg;
    string replyMsgStr;

    //message type
    replyMsgStr = "0230";

    //bit map
    subMsg = "323A00000A008000";
    replyMsgStr.append(subMsg);

    //processing code
    subMsg = msgStr.substr(24, 6);
    replyMsgStr.append(subMsg);

    //amount
    subMsg = msgStr.substr(30, 12);
    replyMsgStr.append(subMsg);

    //date/time
    subMsg = msgStr.substr(42, 10);
    replyMsgStr.append(subMsg);

    //trace number
    subMsg = msgStr.substr(52, 6);
    replyMsgStr.append(subMsg);

    //local time
    subMsg = msgStr.substr(58, 6);
    replyMsgStr.append(subMsg);

    //local date
    subMsg = msgStr.substr(64, 4);
    replyMsgStr.append(subMsg);

    //settelment date
    subMsg = msgStr.substr(72, 4);
    replyMsgStr.append(subMsg);

    //retrieval reference number
    subMsg = msgStr.substr(108, 24);
    replyMsgStr.append(subMsg);

    //responce code
    subMsg = msgStr.substr(144, 4);
    replyMsgStr.append(subMsg);

    //transaction currency code
    subMsg = "0554";
    replyMsgStr.append(subMsg);

    // Get message length
    int length = replyMsgStr.length();
    length = length / 2;
    string msgLength = intToHex(length);
    replyMsgStr = msgLength.append(replyMsgStr);

    message.setReplyMessage(replyMsgStr);


}

if (type == 100) {
    string subMsg;
    string replyMsgStr;

    string processing_code = msgStr.substr(24, 6); // The processing code
    string amount = msgStr.substr(30, 12); // The amount
    string transaction_number = msgStr.substr(52, 6); // The trace number
    string magnetic_number = msgStr.substr(106, 16); // The track2data
    string database = msgStr.substr(112, 2); // Which database we query
    string etsl_number = hexStringToAsciiString(msgStr.substr(130, 24), 12); // The retreival reference number
    string terminal_number = hexStringToAsciiString(msgStr.substr(170, 30), 15);
    ; // The card acceptor id code

    string return_string;
    string return_code;
    string return_value;

    string pinpadMessage;
    string terminalMessage;
    string receiptText1;
    string receiptText2;
    string tmLength;

    // Get response code
    bool rewardOnPurchase;
    stringstream ss;
    double numDouble;
    int numInt;
    ss << database;
    ss >> numInt;

    if (numInt == 10) {
        //cout << "\nProwze Database";

        replyMsgStr = "0110B23A4481AAE180000000000000000080";

        subMsg = msgStr.substr(24, 130);
        replyMsgStr = replyMsgStr.append(subMsg);

        // Get Processing Code and Reward Amount
        rewardOnPurchase = false;
        return_string = prowze_db(processing_code, amount, transaction_number, magnetic_number, etsl_number, terminal_number, rewardOnPurchase);
        //cout << "\nreturn_string: " << return_string << "\n\n";
        return_code = return_string.substr(0, 4);
        //return_code = "3035";
        return_value = return_string.substr(4, 8);
        // Convert return value to hex
        return_value = asciiStringToHexString(return_value, 8);

        //cout << "\nprocessing_code: " << processing_code;
        if (atoi(processing_code.c_str()) == 13000) {
            //cout << "\nReward Transaction";   

            if (atoi(return_code.c_str()) == 3030) {
                //cout << "\nAccepted Reward Transaction";

                //terminalMessage = "20202020414343455054454420202020";
                terminalMessage = terminalMessage.append("2052455741524420");
                terminalMessage = terminalMessage.append(return_value);
                terminalMessage = terminalMessage.append("20202020414343455054454420202020");
                terminalMessage = terminalMessage.append("594F55522052455741524420");
                terminalMessage = terminalMessage.append(return_value);
                terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                string tmLength = "0072";
                terminalMessage = tmLength.append(terminalMessage);
            } else if (atoi(return_code.c_str()) == 3537) {
                //cout << "\nDeclined Reward Transaction: Card On Hold";

                terminalMessage = "202043415244204F4E20484F4C442020";
                terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                terminalMessage = terminalMessage.append("2020202043415244204F4E20484F4C4420202020");
                terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                tmLength = "0072";
                terminalMessage = tmLength.append(terminalMessage);
            } else {
                //cout << "\nDeclined Reward Transaction";

                terminalMessage = "202020204445434C494E454420202020";
                terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                terminalMessage = terminalMessage.append("594F5552205245574152442024303030302E3030");
                terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                tmLength = "0072";
                terminalMessage = tmLength.append(terminalMessage);
            }

        } else if (atoi(processing_code.c_str()) == 3000) {
            //cout << "\nPurchase Transaction";

            if (atoi(return_code.c_str()) == 3030) {
                //cout << "\nAccepted Purchase Transaction";

                // Perform Reward on Purchase
                rewardOnPurchase = true;
                return_string = prowze_db("013000", amount, transaction_number, magnetic_number, etsl_number, terminal_number, rewardOnPurchase);
                //cout << "\nreturn_string: ";
                //return_code = return_string.substr(0,4);
                return_value = return_string.substr(4, 8);
                // Convert return value to hex
                return_value = asciiStringToHexString(return_value, 8);

                terminalMessage = "41434345505420574954482053494720";
                terminalMessage = terminalMessage.append("41434345505420574954482053494720");
                terminalMessage = terminalMessage.append("2020414343455054205749544820534947202020");
                terminalMessage = terminalMessage.append("594F55522052455741524420");
                terminalMessage = terminalMessage.append(return_value);
                string tmLength = "0072";
                terminalMessage = tmLength.append(terminalMessage);
            } else if (atoi(return_code.c_str()) == 3537) {
                //cout << "\nDeclined Reward Transaction: Card On Hold";

                terminalMessage = "202043415244204F4E20484F4C442020";
                terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                terminalMessage = terminalMessage.append("2020202043415244204F4E20484F4C4420202020");
                terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                tmLength = "0072";
                terminalMessage = tmLength.append(terminalMessage);
            } else {
                //cout << "\nDeclined Purchase Transaction";

                terminalMessage = "202020204445434C494E454420202020";
                terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                terminalMessage = terminalMessage.append("594F5552205245574152442024303030302E3030");
                terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                tmLength = "0072";
                terminalMessage = tmLength.append(terminalMessage);

            }


        } else {
            //cout << "\nUnkown Transaction Type";

            // Return Code
            return_code = "3035";

            // Decline message
            terminalMessage = "202020204445434C494E454420202020";
            terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
            terminalMessage = terminalMessage.append("594F5552205245574152442024303030302E3030");
            terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
            tmLength = "0072";
            terminalMessage = tmLength.append(terminalMessage);
        }

        // Append Return Code
        replyMsgStr = replyMsgStr.append(return_code);

        //subMsg = msgStr.substr(154,166);
        //154 = 
        subMsg = msgStr.substr(154);
        replyMsgStr = replyMsgStr.append(subMsg);

        //Check to see if the message is a pre-auth
        //Not pre-auth bit map: 323A4481A8E18000
        //pre-auth bit map: 323A4481A8E18080
        //cout << "\nCheck bit 15 of bitmap to see if message is a pre-auth: " << msgStr.substr(22,1);
        if (!((msgStr.substr(22, 1)).compare("8"))) {
            //cout << ": Therefore pre-auth message";
            int aa = replyMsgStr.length();
            aa = aa - 10;
            replyMsgStr = replyMsgStr.substr(0, aa);
        } else //cout << ": Therefore non pre-auth message";

            // Append Terminal Message
            replyMsgStr = replyMsgStr.append(terminalMessage);

        // Get message length
        int length = replyMsgStr.length();
        length = length / 2;
        string msgLength = intToHex(length);
        replyMsgStr = msgLength.append(replyMsgStr);

        message.setReplyMessage(replyMsgStr);


    } else if (numInt == 20) {
        //cout << "\nBarter Database";

        replyMsgStr = "0110B23A4481AAE180000000000000000080";

        subMsg = msgStr.substr(24, 130);
        replyMsgStr = replyMsgStr.append(subMsg);

        // Get Return Code
        //cout << "\nprocessing_code: " << processing_code << "\n";
        if (atoi(processing_code.c_str()) == 3000) {
            return_code = barter_db(processing_code, amount, transaction_number, magnetic_number, etsl_number, terminal_number);
        } else {
            return_code = "3035";
        }
        //cout << "\nreturn_code: " << return_code;         

        if (atoi(processing_code.c_str()) == 3000) {
            //cout << "\nPurchase Transaction";

            if (atoi(return_code.c_str()) == 3030) {
                //cout << "\nAccepted Purchase Transaction";                    

                //terminalMessage = "20202020414343455054454420202020";     //ACCEPTED
                terminalMessage = "41434345505420574954482053494720"; //ACCEPT WITH SIG
                terminalMessage = terminalMessage.append("41434345505420574954482053494720"); //ACCEPT WITH SIG
                terminalMessage = terminalMessage.append("42415254455253504143452053484F5050494E47"); //BARTERSPACE SHOPPING
                terminalMessage = terminalMessage.append("2020202042415254455253504143452020202020"); //BARTERSPACE
                string tmLength = "0072";
                terminalMessage = tmLength.append(terminalMessage);
            } else if (atoi(return_code.c_str()) == 3537) {
                //cout << "\nDeclined Purchase Transaction: Card On Hold";

                terminalMessage = "202043415244204F4E20484F4C442020";
                terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                terminalMessage = terminalMessage.append("42415254455253504143452053484F5050494E47");
                string tmLength = "0052";
                terminalMessage = tmLength.append(terminalMessage);
            } else {
                //cout << "\nDeclined Purchase Transaction";

                terminalMessage = "202020204445434C494E454420202020";
                terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                terminalMessage = terminalMessage.append("42415254455253504143452053484F5050494E47");
                string tmLength = "0052";
                terminalMessage = tmLength.append(terminalMessage);

            }

        } else {
            //cout << "\nUnkown Transaction Type";

            // Return Code
            return_code = "3035";

            // Decline message
            terminalMessage = "202020204445434C494E454420202020";
            terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
            terminalMessage = terminalMessage.append("42415254455253504143452053484F5050494E47");
            string tmLength = "0052";
            terminalMessage = tmLength.append(terminalMessage);
        }

        // Append Return Code
        replyMsgStr = replyMsgStr.append(return_code);

        //subMsg = msgStr.substr(154,166);
        subMsg = msgStr.substr(154);
        replyMsgStr = replyMsgStr.append(subMsg);

        //Check to see if the message is a pre-auth
        //Not pre-auth bit map: 323A4481A8E18000
        //pre-auth bit map: 323A4481A8E18080
        //cout << "\nCheck bit 15 of bitmap to see if message is a pre-auth: " << msgStr.substr(22,1);
        if (!((msgStr.substr(22, 1)).compare("8"))) {
            //cout << ": Therefore pre-auth message";
            int aa = replyMsgStr.length();
            aa = aa - 10;
            replyMsgStr = replyMsgStr.substr(0, aa);
        } else //cout << ": Therefore non pre-auth message";

            // Append Terminal Message
            replyMsgStr = replyMsgStr.append(terminalMessage);

        // Get message length
        int length = replyMsgStr.length();
        length = length / 2;
        string msgLength = intToHex(length);
        replyMsgStr = msgLength.append(replyMsgStr);

        message.setReplyMessage(replyMsgStr);


    } else {
        //cout << "\nCould Not Find Database";

        //Message type and bit map
        replyMsgStr = "0110323A4481AAE18000";

        subMsg = msgStr.substr(24, 130);
        replyMsgStr = replyMsgStr.append(subMsg);

        // Return Code
        //subMsg = barter_db(processing_code, amount, transaction_number, magnetic_number, etsl_number, terminal_number);
        return_code = "3035";
        replyMsgStr = replyMsgStr.append(return_code);

        subMsg = msgStr.substr(154);
        replyMsgStr = replyMsgStr.append(subMsg);

        // Get message length
        int length = replyMsgStr.length();
        length = length / 2;
        string msgLength = intToHex(length);
        replyMsgStr = msgLength.append(replyMsgStr);

        message.setReplyMessage(replyMsgStr);
    }



    // Put in additional user information
    //replyMsgStr = replyMsgStr.append(terminalMessage);

    // Accept message reward
    /*      string terminalMessage = "20202020414343455054454420202020";
                    terminalMessage = terminalMessage.append("20202020414343455054454420202020");
                    terminalMessage = terminalMessage.append("594F5552205245574152442024303030302E3030");
                    terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                    string tmLength = "0072";
                    terminalMessage = tmLength.append(terminalMessage);
                    replyMsgStr = replyMsgStr.append(terminalMessage);
     */
    // Decline message reward
    /*      terminalMessage = "202020204445434C494E454420202020";
                    terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                    terminalMessage = terminalMessage.append("594F5552205245574152442024303030302E3030");
                    terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                    tmLength = "0072";
                    terminalMessage = tmLength.append(terminalMessage);
                    replyMsgStr = replyMsgStr.append(terminalMessage);
     */
    // Accept message purchase
    /*      string terminalMessage = "20202020414343455054454420202020";
                    terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                    terminalMessage = terminalMessage.append("594F5552205245574152442024303030302E3030");
                    terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                    string tmLength = "0072";
                    terminalMessage = tmLength.append(terminalMessage);
                    replyMsgStr = replyMsgStr.append(terminalMessage);
     */
    // Decline message purchase
    /*      string terminalMessage = "202020204445434C494E454420202020";
                    terminalMessage = terminalMessage.append("202020204445434C494E454420202020");
                    terminalMessage = terminalMessage.append("594F5552205245574152442024393030302E3030");
                    terminalMessage = terminalMessage.append("50524F575A452052455741524453204341534821");
                    string tmLength = "0072";
                    terminalMessage = tmLength.append(terminalMessage);
                    replyMsgStr = replyMsgStr.append(terminalMessage);
     */


} else if (type == 800) {
    string subMsg;

    string replyMsgStr = "001E08108220000002000000";

    subMsg = "0400000000000000";
    replyMsgStr = replyMsgStr.append(subMsg);

    subMsg = msgStr.substr(40, 16);
    replyMsgStr = replyMsgStr.append(subMsg);

    replyMsgStr = replyMsgStr.append("3030");

    subMsg = msgStr.substr(56, 4);
    replyMsgStr = replyMsgStr.append(subMsg);

    message.setReplyMessage(replyMsgStr);
} else if ((type == 420) || (type == 421)) {
    string subMsg;
    string replyMsgStr = "";

    string processing_code = msgStr.substr(40, 6); // The processing code
    string amount = msgStr.substr(46, 12); // The amount
    string transaction_number = msgStr.substr(68, 6); // The trace number
    string magnetic_number = msgStr.substr(122, 16); // The track2data
    string database = msgStr.substr(128, 2); // Which database we query
    string etsl_number = hexStringToAsciiString(msgStr.substr(146, 24), 12); // The retreival reference number

    subMsg = "0430B23A00000A0080000000004000000000";
    replyMsgStr = replyMsgStr.append(subMsg);

    subMsg = msgStr.substr(40, 48);
    replyMsgStr = replyMsgStr.append(subMsg);

    subMsg = msgStr.substr(146, 24);
    ;
    replyMsgStr = replyMsgStr.append(subMsg);






    if (atoi(database.c_str()) == 10) {
        //cout << "\nChecking prowze database for reversal\n";
        subMsg = prowze_db_rev(processing_code, amount, transaction_number, magnetic_number, etsl_number);
        //cout << "\nreturnCode: " << subMsg << "\n";
    } else if (atoi(database.c_str()) == 20) {
        //cout << "\nChecking barter database for reversal\n";
        subMsg = barter_db_rev(processing_code, amount, transaction_number, magnetic_number, etsl_number);
        //cout << "\nreturnCode: " << subMsg << "\n";
    } else {
        subMsg = "3030";
    }
    replyMsgStr = replyMsgStr.append(subMsg);

    //subMsg = msgStr.substr(270,4);
    //replyMsgStr = replyMsgStr.append(subMsg);

    //subMsg = msgStr.substr(318,42);
    //replyMsgStr = replyMsgStr.append(subMsg);

    subMsg = msgStr.substr(316, 46); //changed from 336 to 316 due to the reversal issue,,,,not it should be fixed. 
    replyMsgStr = replyMsgStr.append(subMsg);

    // Get message length
    int length = replyMsgStr.length();
    length = length / 2;
    string msgLength = intToHex(length);
    replyMsgStr = msgLength.append(replyMsgStr);

    message.setReplyMessage(replyMsgStr);
}

}

4

1 に答える 1

2

if (sendLogoff)コードでは、 を作成しているように見えますが、logoffMessageを送信しますlogonMessage。また、メッセージが動的に割り当てられた場合、どこでも割り当てを解除しようとしているとは思いません。

のメモリ割り当てと割り当て解除についても同様の懸念がありますreplyMessage

私は何をするかについての可視性を持っていmessageHandlerません。

ピアに接続されていないソケットに書き込むと、プログラムはSIGPIPE. それを処理するシグナル ハンドラを実装しない場合、プログラムは終了します。sendの代わりにを使用する場合writeは、フラグを渡してMSG_NOSIGNALを抑制しSIGPIPE、代わりにエラー メッセージsendを返すことができます。EPIPE

ソケットをノンブロッキングに設定しているため、短い読み取りと書き込みに関する Loki Astari の警告と、それらに対処するための彼の提案に注意する必要があります。

コマンドはcronジョブから起動されるため、プログラムからの出力が電子メールで送信されているかどうかを確認することをお勧めします。システムで出力の電子メールが無効になっている場合は、cronジョブ エントリを変更して、出力を調査可能なログ ファイルにリダイレクトします。&>bash では、リダイレクトを使用してこれを行うことができます。例えば、

$ command &> /tmp/command.log
于 2012-06-21T23:39:11.650 に答える