Reputation: 5307
Today I was codding something and at some point I needed the getpass function, and everything was OK, well at least until I used --std=c11 and i got:
error: implicit declaration of function ‘getpass’ [-Werror=implicit-function-declaration]|
On internet i found that this function is considered obsolete.:
The getpass() function is not threadsafe because it manipulates global signal state.
The getpass() function is scheduled to be withdrawn from a future version of the X/Open CAE Specification.
So I cannot use it, at least not if I compile with --std=c11.
The program which I tried looks like this:
#include<stdio.h>
#include<unistd.h>
#include<string.h>
#include<stdlib.h>
int main(void){
char checkPasswd[BUFSIZ] = "iajsdiajsda32121312asda:ubuntu";
char *checkName = "michi";
char name[25];
char *passwd;
char *delimiter;
printf("Login Name:\t");
scanf("%24s" ,name);
delimiter = strchr(checkPasswd, ':');
delimiter[0] = '\0';
delimiter++;
passwd = getpass("Give a passwd:\t");
if(strcmp(name,checkName) == 0){
if(strcmp(passwd,delimiter) == 0){
printf("Logged In\n\n");
}else{
printf("\t\t\tWrong Password\n");
exit(1);
}
}else{
printf("\t\t\tWrong Name\n");
exit(1);
}
printf("\t\t\tWelcome %s\n\n", name);
return 0;
}
I read something here ==>> Getting a password in C without using getpass (3)? and there is also some Answers but I was wondering if there is am easy way before i try what i found there, something similar to:
passwd = getpass("Give a passwd:\t");
Or I have to create it my self ?
This program doesn't do what I need:
#include <stdio.h>
#include <stdlib.h>
#include <termios.h>
int main(void){
struct termios oflags, nflags;
char password[64];
tcgetattr(fileno(stdin), &oflags);
nflags = oflags;
nflags.c_lflag &= ~ECHO;
nflags.c_lflag |= ECHONL;
if (tcsetattr(fileno(stdin), TCSANOW, &nflags) != 0) {
perror("tcsetattr");
return EXIT_FAILURE;
}
printf("password: ");
fgets(password, sizeof(password), stdin);
password[strlen(password) - 1] = 0;
printf("you typed '%s'\n", password);
if (tcsetattr(fileno(stdin), TCSANOW, &oflags) != 0) {
perror("tcsetattr");
return EXIT_FAILURE;
}
return 0;
}
So the question is, do I have to write it my self or there is an Alternative function ?
Upvotes: 1
Views: 2765
Reputation: 8286
If your terminal supports these escape codes, this will conceal what you type for a password.
#include <stdio.h>
void UserPW ( char *pw, size_t pwsize) {
int i = 0;
int ch = 0;
printf ( "\033[8m");//conceal typing
while ( 1) {
ch = getchar();
if ( ch == '\r' || ch == '\n' || ch == EOF) {//get characters until CR or NL
break;
}
if ( i < pwsize - 1) {//do not save pw longer than space in pw
pw[i] = ch; //longer pw can be entered but excess is ignored
pw[i + 1] = '\0';
}
i++;
}
printf ( "\033[0A");//move cursor up one line
printf ( "\033[21C");//move cursor 21 places
while ( i) {
printf ( "*");//overwrite password on screen. this is still concealed
i--;
}
printf ( "\033[28m");//reveal typing
}
int main ( ) {
char password[20];
printf ( "Enter your password: ");
fflush ( stdout);//prompt does not have '\n' so make sure it prints
UserPW ( password, sizeof ( password));//password array and size
printf ( "\nentered [%s]\n", password);//instead of printing you would verify the entered password
return 0;
}
Upvotes: 3
Reputation: 317
Let me just give a few comments in your own writing:
getpass()
only reads 8 characters, so don't use it.
Own code should be written in a way that permits to detect whether the user entered more characters than expected.
filedes.h
does not exist and is not needed.
The paswd is usually read either from /dev/tty or from stderr.
If you do not catch important signals, the code may leave the tty in an unusable state.
See the UNIX source code for a working implementation:
Upvotes: 1