From: Egor Date: Tue, 20 Jan 2026 22:20:37 +0000 (+0200) Subject: use new/delete instead of malloc/free X-Git-Url: https://git.patchysicp.xyz/?a=commitdiff_plain;h=e2908234fbfa06c122a6757b8d15fda9437b3e06;p=patchyircd.git use new/delete instead of malloc/free --- diff --git a/src/admin.cpp b/src/admin.cpp index 3a545b3..13f4e0d 100644 --- a/src/admin.cpp +++ b/src/admin.cpp @@ -286,13 +286,13 @@ static int fn_channel_mode(lua_State *L) size_t as, bs; const char *a = luaL_checklstring(L, 2, &as); const char *b = luaL_optlstring(L, 3, 0, &bs); - char *buf = (char *)malloc(as+bs+2); + char *buf = new char[as+bs+2]; memcpy(buf, a, as+1); if (b) memcpy(buf+as+1, b, bs+1); char *args[] = { buf, b ? buf+as+1 : 0, 0 }; channel_mode(0, chan, args); - free(buf); + delete[] buf; return 0; } static int fn_channel_topic(lua_State *L) diff --git a/src/irc.cpp b/src/irc.cpp index b75f4fd..1cde194 100644 --- a/src/irc.cpp +++ b/src/irc.cpp @@ -310,11 +310,9 @@ int irc_process_line(Client *client, char *source, std::string_view command, int // RFC 4616 spec says the three parts of the response can be up to 255 bytes long // That's 255*3 + 2, but we'll add another NUL byte after the pass, so it's 768. // Base64 encoding adds 4/3 overhead, so the total buffer size is 1024. - client->saslbuf = (char *)malloc(1024); + client->saslbuf = new char[1024]; client->saslbufLen = 0; client->saslexternal = !strcmp(args[0], "EXTERNAL"); - if (!client->saslbuf) - abortf("malloc fail (saslbuf)\n"); } else { size_t len = strlen(args[0]); // there are three cases @@ -396,7 +394,7 @@ int irc_process_line(Client *client, char *source, std::string_view command, int } else { err_saslfail(), sendbuf(client); } - free(client->saslusername); + delete[] client->saslusername; client->saslusername = 0; newUser(client); } @@ -404,8 +402,6 @@ int irc_process_line(Client *client, char *source, std::string_view command, int // we'll clear the whole buffer later, this is just in case username alloc fails memset(password, 0, strlen(password)); client->saslusername = mystrdup(username); - if (!client->saslusername) - abortf("strdup fail (saslusername)\n"); goto saslcleanup; } else { #ifdef HAVE_LIBTLS @@ -427,7 +423,7 @@ saslerr: err_saslfail(), sendbuf(client); saslcleanup: memset(client->saslbuf, 0, 1024); - free(client->saslbuf); + delete[] client->saslbuf; client->saslbuf = 0; client->saslbufLen = 0; return 0; @@ -440,10 +436,8 @@ saslcleanup: if (is_registered(client)) { setNick(client, args[0]); } else { - free(client->nick_reg); + delete[] client->nick_reg; client->nick_reg = mystrdup(args[0]); - if (!client->nick_reg) - abortf("strdup fail (nick_reg)\n"); newUser(client); } } MATCH_COMMAND("USER") { @@ -457,10 +451,8 @@ saslcleanup: client_chghost(client, args[0]-1, 0); } // set realname - free(client->realname); + delete[] client->realname; client->realname = mystrdup(args[3]); - if (!client->realname) - abortf("strdup fail (realname)\n"); // proceed with registration newUser(client); } MATCH_COMMAND("PASS") { @@ -472,12 +464,10 @@ saslcleanup: return err_needmoreparams(client, command), sendbuf(client), 0; if (client->pass_reg) { memset(client->pass_reg, 0, strlen(client->pass_reg)); - free(client->pass_reg); + delete[] client->pass_reg; } client->pass_reg = mystrdup(args[0]); memset(args[0], 0, strlen(args[0])); - if (!client->pass_reg) - abortf("strdup fail (pass_reg)\n"); } MATCH_COMMAND("WEBIRC") { if (is_registered(client)) return err_alreadyregistered(client), sendbuf(client), 0; @@ -491,23 +481,21 @@ saslcleanup: client->webircwait = 2; if (!strcmp(args[1], "biboumi")) { size_t len = strlen(args[2]); - client->webirchostname = (char *)malloc(len+sizeof(".xmpp")); - if (client->webirchostname) { - memcpy(client->webirchostname, args[2], len); - memcpy(client->webirchostname+len, ".xmpp", sizeof(".xmpp")); - } + client->webirchostname = new char[len+sizeof(".xmpp")]; + memcpy(client->webirchostname, args[2], len); + memcpy(client->webirchostname+len, ".xmpp", sizeof(".xmpp")); } job_password_check(client, args[1], args[0], "webirc", [client](int res) { if (!(client->umode & UMODE_SECURE) || res != 0) { - free(client->webircpeername); + delete[] client->webircpeername; client->webircpeername = 0; err_passwdmismatch(client), sendbuf(client); } else { - free(client->peername); + delete[] client->peername; client->peername = client->webircpeername; if (client->webirchostname) { client_chghost(client, 0, client->webirchostname); - free(client->webirchostname); + delete[] client->webirchostname; client->webirchostname = 0; } client->webircpeername = 0; @@ -1132,13 +1120,11 @@ privmsg_notice_common: if (!is_registered(client)) return err_notregistered(client), sendbuf(client), 0; if (args[0]) { - free(client->away); + delete[] client->away; client->away = mystrdup(args[0]); - if (!client->away) - abortf("strdup fail (away)\n"); rpl_nowaway(client), sendbuf(client); } else { - free(client->away); + delete[] client->away; client->away = NULL; rpl_unaway(client), sendbuf(client); } @@ -1217,7 +1203,7 @@ privmsg_notice_common: return err_notregistered(client), sendbuf(client), 0; if (argc == 0) return err_needmoreparams(client, command), sendbuf(client), 0; - free(client->realname); + delete[] client->realname; client->realname = mystrdup(args[0]); msg_setname(client); int cookie = sendbuf_visible_caps(client, CAP_SETNAME, 0); @@ -1244,7 +1230,7 @@ void newUser(Client *client) { err_saslaborted(), sendbuf(client); if (client->saslbuf) { memset(client->saslbuf, 0, 1024); - free(client->saslbuf); + delete[] client->saslbuf; client->saslbuf = 0; client->saslbufLen = 0; } @@ -1263,12 +1249,12 @@ void newUser(Client *client) { }); client->passwait = 1; memset(client->pass_reg, 0, strlen(client->pass_reg)); - free(client->pass_reg); + delete[] client->pass_reg; client->pass_reg = NULL; return; } setNick(client, client->nick_reg); - free(client->nick_reg); + delete[] client->nick_reg; client->nick_reg = NULL; client->signon = client->lastactivity = get_time(); if (!client->nick) @@ -1342,10 +1328,8 @@ static void updateNuh(Client *client) { const char *n = client->nick ? client->nick : "*"; const char *u = client->username ? client->username : "*"; const char *h = client->hostname; - free(client->nuh); - client->nuh = (char *)malloc(strlen(n) + strlen(u) + strlen(h) + 3); - if (!client->nuh) - abortf("malloc fail (nuh)\n"); + delete[] client->nuh; + client->nuh = new char[strlen(n) + strlen(u) + strlen(h) + 3]; sprintf(client->nuh, "%s!%s@%s", n, u, h); stringlower(client->nuh); } @@ -1390,8 +1374,8 @@ void setNick(Client *client, char* nickname) { chan->o.rename(client, key); chan->v.rename(client, key); } - free(client->nick); - free(client->key); + delete[] client->nick; + delete[] client->key; } else { #ifdef HAVE_LUA admin_hook("nickadd", client, 0, 0, key); @@ -1399,12 +1383,8 @@ void setNick(Client *client, char* nickname) { } client->nick = mystrdup(nickname); - if (!client->nick) - abortf("strdup fail (nickname)\n"); updateNuh(client); client->key = mystrdup(key); - if (!client->key) - abortf("strdup fail (key)\n"); client_map.add(client); rpl_mononline(0, client), sendbuf_monitor(client->key, 0, 0, 0); return; @@ -1446,17 +1426,13 @@ void client_chghost(Client *client, const char *newusername, const char *newhost if (newusername == client->username+1) { memmove(client->username, client->username+1, strlen(client->username)); } else if (newusername) { - free(client->username); + delete[] client->username; client->username = mystrdup(newusername); - if (!client->username) - abortf("strdup fail (username)\n"); } // update hostname if (newhostname) { - free(client->hostname); + delete[] client->hostname; client->hostname = mystrdup(newhostname); - if (!client->hostname) - abortf("strdup fail (hostname)\n"); } // update nuh updateNuh(client); @@ -1589,19 +1565,13 @@ void channel_join(Client *client, const char *channel, const char *chankey) } Channel *channel_new(const char *channel, const char *key, time_t creation) { - Channel *chan = (Channel *)malloc(sizeof(Channel)); - if (!chan) - abortf("malloc fail (channel)\n"); + Channel *chan = new Channel(); memset(chan, 0, sizeof(Channel)); chan->creation = creation; chan->member_limit = -1; chan->dmode = DMODE_NOEXTERNAL | DMODE_TOPICPROT | DMODE_PERSIST; chan->key = mystrdup(key); - if (!chan->key) - abortf("strdup fail (key)\n"); chan->name = mystrdup(channel); - if (!chan->name) - abortf("strdup fail (name)\n"); return chan; } void channel_part(Client *client, Channel *chan, const char *reason, Client *kicker) @@ -1625,25 +1595,27 @@ void channel_part(Client *client, Channel *chan, const char *reason, Client *kic } void channel_kill(Channel *chan) { - channel_map.remove(chan); - for (auto cl : chan->invitees) - cl->invites.remove(chan); - free(chan->key); - free(chan->name); - free(chan->topic); - free(chan->topic_who); - chan->members.clear(); - chan->o.clear(); - chan->v.clear(); - chan->listb.clear(); - chan->liste.clear(); - chan->listI.clear(); - chan->listq.clear(); - chan->listwo.clear(); - chan->listwv.clear(); - chan->invitees.clear(); - free(chan->chankey); - free(chan); + delete chan; +} +Channel::~Channel() { + channel_map.remove(this); + for (auto cl : invitees) + cl->invites.remove(this); + delete[] key; + delete[] name; + delete[] topic; + delete[] topic_who; + members.clear(); + o.clear(); + v.clear(); + listb.clear(); + liste.clear(); + listI.clear(); + listq.clear(); + listwo.clear(); + listwv.clear(); + invitees.clear(); + delete[] chankey; } void channel_mode(Client *client, Channel *chan, char *args[]) { const char *n = client ? client->nick : "cia"; @@ -1718,13 +1690,10 @@ void channel_mode(Client *client, Channel *chan, char *args[]) { args++; break; } - if (chan->chankey) - free(chan->chankey); + delete[] chan->chankey; chan->chankey = mystrdup(*args); - if (!chan->chankey) - abortf("strdup fail (chankey)\n"); } else { - free(chan->chankey); + delete[] chan->chankey; chan->chankey = NULL; if (*args) // unused argument args++; @@ -1813,19 +1782,15 @@ void channel_mode(Client *client, Channel *chan, char *args[]) { } void channel_topic(Client *src, Channel *chan, const char *topic, const char *who, time_t when) { - free(chan->topic); - free(chan->topic_who); + delete[] chan->topic; + delete[] chan->topic_who; if (!*topic) { chan->topic = NULL; chan->topic_who = NULL; chan->topic_when = 0; } else { chan->topic = mystrdup(topic); - if (!chan->topic) - abortf("strdup fail (topic)\n"); chan->topic_who = mystrdup(who); - if (!chan->topic_who) - abortf("strdup fail (topic_who)\n"); chan->topic_when = when; } if (src) diff --git a/src/ircdata.hpp b/src/ircdata.hpp index 36b4c2d..dcef261 100644 --- a/src/ircdata.hpp +++ b/src/ircdata.hpp @@ -72,6 +72,11 @@ struct Client { unsigned saslexternal :1; unsigned passwait :1; unsigned webircwait :2; + + Client() = default; + Client(const Client&) = delete; + Client& operator=(const Client&) = delete; + ~Client(); }; struct Channel { char *key; @@ -94,6 +99,11 @@ struct Channel { clientmap invitees; char *chankey; int member_limit; + + Channel() = default; + Channel(const Channel&) = delete; + Channel& operator=(const Channel&) = delete; + ~Channel(); }; #define DMODE_PERSIST 1 #define DMODE_INVITEONLY 2 diff --git a/src/main.cpp b/src/main.cpp index d2848fe..80e1aeb 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -146,8 +146,6 @@ static void accept_from_sock(struct listener *listener) cl->fd = fd; cl->cctx = cctx; cl->peername = mystrdup(client_addr); - if (!cl->peername) - abortf("strdup fail (peername)\n"); cl->peerport = port; if (cctx) cl->umode |= UMODE_SECURE; @@ -322,12 +320,10 @@ int main(int argc, char *argv[]) if (sp && bang && bang < sp) { size_t nlen = bang - p - 1; if (memcmp(&p[1], fake->nick, nlen) != 0) { - char *nnick = (char *)malloc(nlen+1); - if (!nnick) - abortf("malloc fail (fake->nick)\n"); + char *nnick = new char[nlen+1]; memcpy(nnick, &p[1], nlen); nnick[nlen] = '\0'; - free(fake->nick); + delete[] fake->nick; fake->nick = nnick; } } diff --git a/src/map.cpp b/src/map.cpp index 5455828..2463ccc 100644 --- a/src/map.cpp +++ b/src/map.cpp @@ -16,7 +16,7 @@ void *map_base::_get(const char *key) size_t i = ent_find(this, key, &found); return found ? ptr[i].value : 0; } -int map_base::_set(const char *key, const void *value, void **oldvalue) +void map_base::_set(const char *key, const void *value, void **oldvalue) { int found; size_t i = ent_find(this, key, &found); @@ -24,7 +24,7 @@ int map_base::_set(const char *key, const void *value, void **oldvalue) if (oldvalue) *oldvalue = ptr[i].value; if (!value) { - free(ptr[i].key); + delete[] ptr[i].key; std::copy(ptr+i+1, ptr+len, ptr+i); len--; } else { @@ -36,16 +36,13 @@ int map_base::_set(const char *key, const void *value, void **oldvalue) if (value) { if (len == cap) { size_t ncap = cap ? cap*2 : 2; - map_value *nptr = (map_value *)realloc(ptr, sizeof(map_value)*ncap); - if (!nptr) - return -1; + map_value *nptr = new map_value[ncap]; + memcpy(nptr, ptr, cap*sizeof(map_value)); ptr = nptr; cap = ncap; } size_t slen = strlen(key)+1; - char *nkey = (char *)malloc(slen); - if (!nkey) - return -1; + char *nkey = new char[slen]; memcpy(nkey, key, slen); std::copy_backward(ptr+i, ptr+len, ptr+len+1); len++; @@ -53,14 +50,13 @@ int map_base::_set(const char *key, const void *value, void **oldvalue) ptr[i].value = const_cast(value); } } - return 0; } void map_base::clear() { while (len) { - free(ptr[--len].key); + delete[] ptr[--len].key; } - free(ptr); + delete[] ptr; ptr = 0; len = cap = 0; } diff --git a/src/map.hpp b/src/map.hpp index 5530dc6..86e7bc7 100644 --- a/src/map.hpp +++ b/src/map.hpp @@ -25,11 +25,10 @@ struct map_base { * Dynarr complexity: O(log n) */ void *_get(const char *key); /* Associate a new value with a given key. - * Returns 0 on success, -1 on allocation error. * If oldvalue is not NULL, it receives the old value of key. * No allocation failures on value = NULL. * Dynarr complexity: O(n) */ - [[nodiscard]] int _set(const char *key, const void *value, void **oldvalue); + void _set(const char *key, const void *value, void **oldvalue); /* Removes all keys from the map and frees any associated memory. * The map_t is reset to zero-initialized state and can be used again. * Dynarr complexity: O(n) */ @@ -94,8 +93,7 @@ public: } bool add(V v) { void *old; - if (_set(T::to_key(v), v, &old) == -1) - abortf("map_base2::add: allocation failure\n"); + _set(T::to_key(v), v, &old); return !old; } bool remove(V v) { @@ -112,8 +110,8 @@ public: struct Client; struct clientmap : map_base2 { void rename(Client *v, const char *newk) { - if (remove(v) && _set(newk, v, 0) == -1) - abortf("clientmap::rename: allocation failure\n"); + remove(v); + _set(newk, v, 0); } }; struct Channel; diff --git a/src/net.cpp b/src/net.cpp index 8bed8d2..7948bff 100644 --- a/src/net.cpp +++ b/src/net.cpp @@ -130,26 +130,28 @@ void killConnectionPart2(Client *cl) } } /* Free all the remaining data */ - free(cl->nick); - free(cl->key); - free(cl->username); - free(cl->realname); - free(cl->hostname); - free(cl->nuh); - free(cl->away); - free(cl->nick_reg); - if (cl->pass_reg) - memset(cl->pass_reg, 0, strlen(cl->pass_reg)); - free(cl->pass_reg); - free(cl->peername); - if (cl->saslbuf) - memset(cl->saslbuf, 0, 1024); - free(cl->saslbuf); - free(cl->saslusername); - free(cl->webircpeername); - free(cl->webirchostname); delete cl; } +Client::~Client() { + delete[] nick; + delete[] key; + delete[] username; + delete[] realname; + delete[] hostname; + delete[] nuh; + delete[] away; + delete[] nick_reg; + if (pass_reg) + memset(pass_reg, 0, strlen(pass_reg)); + delete[] pass_reg; + delete[] peername; + if (saslbuf) + memset(saslbuf, 0, 1024); + delete[] saslbuf; + delete[] saslusername; + delete[] webircpeername; + delete[] webirchostname; +} void read_proc(Client *cl) { diff --git a/src/util.cpp b/src/util.cpp index b75623d..14c056d 100644 --- a/src/util.cpp +++ b/src/util.cpp @@ -71,9 +71,8 @@ void stringlower(char *s) { } char *mystrdup(const char *s) { size_t len = strlen(s); - char *buf = (char *)malloc(len+1); - if (buf) - memcpy(buf, s, len+1); + char *buf = new char[len+1]; + memcpy(buf, s, len+1); return buf; } diff --git a/src/util.hpp b/src/util.hpp index 0eed7b2..ff349f6 100644 --- a/src/util.hpp +++ b/src/util.hpp @@ -16,6 +16,10 @@ void stringlower(char *s); #pragma GCC poison strcat #pragma GCC poison strncat #pragma GCC poison abort +#pragma GCC poison malloc +#pragma GCC poison calloc +#pragma GCC poison realloc +#pragma GCC poison free #endif #define strcpy_lit(a, b) memcpy((a), (b), sizeof(b)) char *mystrdup(const char *s);