+/* check if we should exit a client due to authd decision
+ * inputs - client server, client connecting
+ * outputs - true if exited, false if not
+ * side effects - messages/exits client if authd rejected and not exempt
+ */
+static bool
+authd_check(struct Client *client_p, struct Client *source_p)
+{
+ struct ConfItem *aconf = source_p->localClient->att_conf;
+ rb_dlink_list varlist = { NULL, NULL, 0 };
+ bool reject = false;
+ char *reason;
+
+ if(source_p->preClient->auth.accepted == true)
+ return reject;
+
+ substitution_append_var(&varlist, "nick", source_p->name);
+ substitution_append_var(&varlist, "ip", source_p->sockhost);
+ substitution_append_var(&varlist, "host", source_p->host);
+ substitution_append_var(&varlist, "dnsbl-host", source_p->preClient->auth.data);
+ substitution_append_var(&varlist, "network-name", ServerInfo.network_name);
+ reason = substitution_parse(source_p->preClient->auth.reason, &varlist);
+
+ switch(source_p->preClient->auth.cause)
+ {
+ case 'B': /* DNSBL */
+ {
+ struct DNSBLEntryStats *stats;
+ char *dnsbl_name = source_p->preClient->auth.data;
+
+ if(dnsbl_stats != NULL)
+ if((stats = rb_dictionary_retrieve(dnsbl_stats, dnsbl_name)) != NULL)
+ stats->hits++;
+
+ if(IsExemptKline(source_p) || IsConfExemptDNSBL(aconf))
+ {
+ sendto_one_notice(source_p, ":*** Your IP address %s is listed in %s, but you are exempt",
+ source_p->sockhost, dnsbl_name);
+ break;
+ }
+
+ sendto_realops_snomask(SNO_REJ, L_NETWIDE,
+ "Listed on DNSBL %s: %s (%s@%s) [%s] [%s]",
+ dnsbl_name, source_p->name, source_p->username, source_p->host,
+ IsIPSpoof(source_p) ? "255.255.255.255" : source_p->sockhost,
+ source_p->info);
+
+ sendto_one(source_p, form_str(ERR_YOUREBANNEDCREEP),
+ me.name, source_p->name, reason);
+
+ sendto_one_notice(source_p, ":*** Your IP address %s is listed in %s",
+ source_p->sockhost, dnsbl_name);
+ add_reject(source_p, NULL, NULL, NULL, "Banned (listed in a DNSBL)");
+ exit_client(client_p, source_p, &me, "Banned (listed in a DNSBL)");
+ reject = true;
+ }
+ break;
+ case 'O': /* OPM */
+ {
+ char *proxy = source_p->preClient->auth.data;
+ char *port = strrchr(proxy, ':');
+
+ if(port == NULL)
+ {
+ /* This shouldn't happen, better tell the ops... */
+ ierror("authd sent us a malformed OPM string %s", proxy);
+ sendto_realops_snomask(SNO_GENERAL, L_ALL,
+ "authd sent us a malformed OPM string %s", proxy);
+ break;
+ }
+
+ /* Terminate the proxy type */
+ *(port++) = '\0';
+
+ if(IsExemptKline(source_p) || IsConfExemptProxy(aconf))
+ {
+ sendto_one_notice(source_p,
+ ":*** Your IP address %s has been detected as an open proxy (type %s, port %s), but you are exempt",
+ source_p->sockhost, proxy, port);
+ break;
+ }
+ sendto_realops_snomask(SNO_REJ, L_NETWIDE,
+ "Open proxy %s/%s: %s (%s@%s) [%s] [%s]",
+ proxy, port,
+ source_p->name,
+ source_p->username, source_p->host,
+ IsIPSpoof(source_p) ? "255.255.255.255" : source_p->sockhost,
+ source_p->info);
+
+ sendto_one(source_p, form_str(ERR_YOUREBANNEDCREEP),
+ me.name, source_p->name, reason);
+
+ sendto_one_notice(source_p,
+ ":*** Your IP address %s has been detected as an open proxy (type %s, port %s)",
+ source_p->sockhost, proxy, port);
+ add_reject(source_p, NULL, NULL, NULL, "Banned (Open proxy)");
+ exit_client(client_p, source_p, &me, "Banned (Open proxy)");
+ reject = true;
+ }
+ break;
+ default: /* Unknown, but handle the case properly */
+ if(IsExemptKline(source_p))
+ {
+ sendto_one_notice(source_p,
+ ":*** You were rejected, but you are exempt (reason: %s)",
+ reason);
+ break;
+ }
+ sendto_realops_snomask(SNO_REJ, L_NETWIDE,
+ "Rejected by authentication system (reason %s): %s (%s@%s) [%s] [%s]",
+ reason, source_p->name, source_p->username, source_p->host,
+ IsIPSpoof(source_p) ? "255.255.255.255" : source_p->sockhost,
+ source_p->info);
+
+ sendto_one(source_p, form_str(ERR_YOUREBANNEDCREEP),
+ me.name, source_p->name, reason);
+
+ sendto_one_notice(source_p, ":*** Rejected by authentication system: %s",
+ reason);
+ add_reject(source_p, NULL, NULL, NULL, "Banned (authentication system)");
+ exit_client(client_p, source_p, &me, "Banned (authentication system)");
+ reject = true;
+ break;
+ }
+
+ if(reject)
+ ServerStats.is_ref++;
+
+ substitution_free(&varlist);
+
+ return reject;
+}
+