X-Git-Url: http://git.pk910.de/?p=ircu2.10.12-pk.git;a=blobdiff_plain;f=ircd%2Fs_auth.c;fp=ircd%2Fs_auth.c;h=112fdc8cf87946de03e7f64cbc02b1fb7ed72ee0;hp=71c86385db89e66b589a99c4abae9ecc37da5a65;hb=96f1ae9c934d475960c2aa6b3b4f1336c37833c2;hpb=fa4486fe3e166152a57a42320fd1f2faee37b0c3 diff --git a/ircd/s_auth.c b/ircd/s_auth.c index 71c8638..112fdc8 100644 --- a/ircd/s_auth.c +++ b/ircd/s_auth.c @@ -84,6 +84,7 @@ enum AuthRequestFlag { AR_NEEDS_USER, /**< user must send USER command */ AR_NEEDS_NICK, /**< user must send NICK command */ AR_LAST_SCAN = AR_NEEDS_NICK, /**< maximum flag to scan through */ + AR_ZOMBIE_RECOVER, /**< nick of user is already taken by a zombie - try to recover */ AR_IAUTH_PENDING, /**< iauth request sent, waiting for response */ AR_IAUTH_HURRY, /**< we told iauth to hurry up */ AR_IAUTH_USERNAME, /**< iauth sent a username (preferred or forced) */ @@ -109,6 +110,7 @@ struct AuthRequest { unsigned int cookie; /**< cookie the user must PONG */ unsigned short port; /**< client's remote port number */ unsigned int numeric; /**< unregistered client numeric */ + struct Client* recover_client; /**< zombie client to be recovered later */ char loc_user[ACCOUNTLEN]; char loc_pass[PASSWDLEN]; }; @@ -134,6 +136,7 @@ static struct { MSG("NOTICE AUTH :*** Checking login\r\n"), MSG("NOTICE AUTH :*** Login rejected\r\n"), MSG("NOTICE AUTH :*** Login accepted\r\n"), + MSG("NOTICE AUTH :*** Nickname in Use by Zombie - try to recover\r\n"), #undef MSG }; @@ -150,7 +153,8 @@ typedef enum { REPORT_INVAL_DNS, REPORT_DO_LOC, REPORT_FAIL_LOC, - REPORT_DONE_LOC + REPORT_DONE_LOC, + REPORT_ZOMBIE_RECOVER } ReportType; /** Sends response \a r (from #ReportType) to client \a c. */ @@ -557,10 +561,27 @@ static int check_auth_finished(struct AuthRequest *auth) if (IsUserPort(auth->client)) { + if(FlagHas(&auth->flags, AR_ZOMBIE_RECOVER)) { + /* check if able to recover connection */ + if(!IsAccount(auth->client) || ircd_strcmp(cli_user(auth->client)->account, cli_user(auth->recover_client)->account)) { + send_reply(auth->client, ERR_RECOVERDENIED, cli_name(auth->recover_client), "auth missmatch"); + + /* reset nickname */ + FlagSet(&auth->flags, AR_NEEDS_NICK); + send_reply(auth->client, ERR_NICKNAMEINUSE, cli_name(auth->recover_client)); + hRemClient(auth->client); + (cli_name(auth->client))[0] = '\0'; + return 0; + } + } memset(cli_passwd(auth->client), 0, sizeof(cli_passwd(auth->client))); res = auth_set_username(auth); if (res == 0) res = register_user(auth->client, auth->client); + if (res == 0 && FlagHas(&auth->flags, AR_ZOMBIE_RECOVER)) { + unzombie_client(&me, &me, auth->client, auth->recover_client); + auth->client = auth->recover_client; + } } else res = 0; @@ -1404,6 +1425,17 @@ int auth_set_user(struct AuthRequest *auth, const char *username, const char *ho return check_auth_finished(auth); } +/** Set Zombie Client that should be recovered later + */ +int auth_set_recover_client(struct AuthRequest *auth, struct Client *zombie) +{ + assert(auth != NULL); + FlagSet(&auth->flags, AR_ZOMBIE_RECOVER); + auth->recover_client = zombie; + + sendheader(auth->client, REPORT_ZOMBIE_RECOVER); +} + /** Handle authorization-related aspects of initial nickname selection. * This is called after verifying that the nickname is available. * @param[in] auth Authorization request for client. @@ -1414,6 +1446,7 @@ int auth_set_nick(struct AuthRequest *auth, const char *nickname) { assert(auth != NULL); FlagClr(&auth->flags, AR_NEEDS_NICK); + /* * If the client hasn't gotten a cookie-ping yet, * choose a cookie and send it. -record!jegelhof@cloud9.net