1

これは私のコードです:

  void get_pass(char *p);

int main(){

    char *host, *user, *pass;

    host = malloc(64); /* spazio per max 64 caratteri */
    if(!host) abort(); /* se malloc ritorna NULL allora termino l'esecuzione */
    host[63] = '\0';   /* evitare un tipo di buffer overflow impostando l'ultimo byte come NUL byte */

    user = malloc(64);
    if(!user) abort();
    user[63] = '\0';

    pass = malloc(64);
    if(!pass) abort();
    pass[63] = '\0';

    /* Immissione di hostname, username e password; controllo inoltre i 'return code' dei vari fscanf e, se non sono 0, esco */
    fprintf(stdout,"--> Inserisci <hostname>: ");
    if(fscanf(stdin, "%63s", host) == EOF){
        fprintf(stdout, "\nErrore, impossibile leggere i dati\n");
        exit(EXIT_FAILURE);
    }
    fprintf(stdout,"\n--> Inserisci <username>: ");
    if(fscanf(stdin, "%63s", user) == EOF){
        fprintf(stdout, "\nErrore, impossibile leggere i dati\n");
        exit(EXIT_FAILURE);
    };
    fprintf(stdout, "\n--> Inserisci <password>: ");
    get_pass(pass);

    /* Stampo a video le informazioni immesse */
    fprintf(stdout, "\n\nHost: %s\nUser: %s\nPass: %s\n\n", host,user,pass);

    /* Azzero il buffer della password e libero la memoria occupata */
    memset(pass,0,(strlen(pass)+1));
    free(host);
    free(user);
    free(pass);

    return EXIT_SUCCESS;
}

void get_pass(char *p){
    /* Grazie a termios.h posso disabilitare l'echoing del terminale (password nascosta) */
    struct termios term, term_orig;
    tcgetattr(STDIN_FILENO, &term);
        term_orig = term;
        term.c_lflag &= ~ECHO;
        tcsetattr(STDIN_FILENO, TCSANOW, &term);
        /* Leggo la password e controllo il 'return code' di fscanf */
        if(fscanf(stdin, "%63s", p) == EOF){
        fprintf(stdout, "\nErrore, impossibile leggere i dati\n");
        tcsetattr(STDIN_FILENO, TCSANOW, &term_orig);
        exit(EXIT_FAILURE);
    };
        /* Reimposto il terminale allo stato originale */
        tcsetattr(STDIN_FILENO, TCSANOW, &term_orig);
}

関数 get_pass にコードがないことが正しいかどうか知りたいreturnですか?

この関数では、パスワードを読み取り、fscanfそれをメインプログラムに返さなければならないと思います...しかし:

  1. 方法がわからない(return p;警告が表示された)
  2. なくても動作return p;するので大丈夫だと思いますが...よくわかりません...

return が関数でどのように機能するかわかりません。

4

4 に答える 4

2
int main() 
{
   char * password = NULL;

   get_pass(&password); //that is how you want to pass pointer to pointer

}

void get_pass(char **password) 
{

//1. get password using scanf from stdin or whatever way you want. 
//2. assign it to *password 
//3. no need to return anything

}

パスワード文字列のメモリ割り当てを処理する必要があることを忘れないでください。パスワードサイズをMAX_PASS_SIZEに固定し、スタックメモリを破損しないようにmain()またはget_passのいずれかにその量のメモリを割り当てたいとします。私が書いた上記のスニペットは、パスワードに値を入力する方法を示しています。これはおそらくあなたの主な質問です。つまり、ポインターをポインターに渡します。

于 2012-05-02T22:02:31.560 に答える
2
  1. 戻り値の型を持つ関数はvoid何も返すべきではありません。
  2. このステートメントを使用してreturn;、いつでも関数から呼び出し元に戻ることができます。
  3. return;ステートメントに到達せず、関数が最後に到達した場合、制御は呼び出し元に返されます。
于 2012-05-02T21:43:52.663 に答える
1

パスワードにスペースを入れたい場合は、次のようなものを使用できます。を使用する代わりに、ラインバッファリングをオフにして、一度に1文字ずつパスワードを処理しますfscanf

    #include <stdio.h>
    #include <errno.h>
    #include <termios.h>
    #include <unistd.h>
    #include <stdlib.h>
    #include <string.h>

    void get_pass(char *p);
    void flushStdin( void );

    int main(){
        // what you have now in your code.
    }



    void flushStdin( void )
    {
        int c;

        while ((c = getchar()) != '\n' && c != EOF);

        return;
    }


    void get_pass(char *p){

    int i = 0;
    int c;
    /* Grazie a termios.h posso disabilitare l'echoing del terminale (password nascosta) */
    struct termios term, term_orig;

    tcgetattr(STDIN_FILENO, &term);

    term_orig = term;
    term.c_lflag &= ~ECHO;
    term.c_lflag &= ~ICANON;
    tcsetattr(STDIN_FILENO, TCSANOW, &term);
    /* Leggo la password e controllo il 'return code' di fscanf */

    flushStdin();
    while( (( c = getchar() ) != '\n') && (i < 63) )
    {
        if( c != 127 )  // did user hit the backspace key?
        {
            p[i++] = (char)c;
        }
        else
        {
            // null last character in password and backup to one space in string
            // should make sure i doesn't go negative... oops.
            if( i > 0 )
            {
                p[--i] = 0x00;
            }
        }
    }

    tcsetattr(STDIN_FILENO, TCSANOW, &term_orig);

    return;
}
于 2012-05-02T23:09:33.687 に答える
1

get_pass は何もない void を返すように定義されています。この場合、戻り値はパラメーター p を介して渡されます。

于 2012-05-02T21:43:57.843 に答える