This is an automated email from Gerrit.

"Antonio Borneo <[email protected]>" just uploaded a new patch set to 
Gerrit, which you can find at https://review.openocd.org/c/openocd/+/9377

-- gerrit

commit 7147e8e51549e7d96c92f395e4e79695533c6130
Author: Antonio Borneo <[email protected]>
Date:   Sun Jan 4 18:24:16 2026 +0100

    server: don't copy each field in struct service_driver
    
    The content of the struct service_driver is not changed during the
    life of the service.
    
    Instead of copying each field of the struct, just keep a pointer
    to the struct itself.
    
    To minimize the change, duplicate in struct service::name the
    field struct service_driver::name.
    
    Change-Id: Ided813facc5d8587de2402f6f4224aec310e94d7
    Signed-off-by: Antonio Borneo <[email protected]>

diff --git a/src/server/gdb_server.c b/src/server/gdb_server.c
index 7b3cc21417..1c40386766 100644
--- a/src/server/gdb_server.c
+++ b/src/server/gdb_server.c
@@ -3872,11 +3872,12 @@ static void gdb_keep_client_alive(struct connection 
*connection)
 
 static const struct service_driver gdb_service_driver = {
        .name = "gdb",
-       .new_connection_during_keep_alive_handler = NULL,
-       .new_connection_handler = gdb_new_connection,
-       .input_handler = gdb_input,
-       .connection_closed_handler = gdb_connection_closed,
-       .keep_client_alive_handler = gdb_keep_client_alive,
+       .new_connection_during_keep_alive = NULL,
+       .new_connection = gdb_new_connection,
+       .input = gdb_input,
+       .service_dtor = NULL,
+       .connection_closed = gdb_connection_closed,
+       .keep_client_alive = gdb_keep_client_alive,
 };
 
 static int gdb_target_start(struct target *target, const char *port)
diff --git a/src/server/ipdbg.c b/src/server/ipdbg.c
index 466717c468..b321c30a14 100644
--- a/src/server/ipdbg.c
+++ b/src/server/ipdbg.c
@@ -740,11 +740,12 @@ static int ipdbg_on_connection_closed(struct connection 
*connection)
 
 static const struct service_driver ipdbg_service_driver = {
        .name = "ipdbg",
-       .new_connection_during_keep_alive_handler = NULL,
-       .new_connection_handler = ipdbg_on_new_connection,
-       .input_handler = ipdbg_on_connection_input,
-       .connection_closed_handler = ipdbg_on_connection_closed,
-       .keep_client_alive_handler = NULL,
+       .new_connection_during_keep_alive = NULL,
+       .new_connection = ipdbg_on_new_connection,
+       .input = ipdbg_on_connection_input,
+       .service_dtor = NULL,
+       .connection_closed = ipdbg_on_connection_closed,
+       .keep_client_alive = NULL,
 };
 
 static struct ipdbg_hub *ipdbg_get_hub_by_name(const char *name)
diff --git a/src/server/rtt_server.c b/src/server/rtt_server.c
index b44101c3dc..ab9a6f799a 100644
--- a/src/server/rtt_server.c
+++ b/src/server/rtt_server.c
@@ -146,11 +146,12 @@ static int rtt_input(struct connection *connection)
 
 static const struct service_driver rtt_service_driver = {
        .name = "rtt",
-       .new_connection_during_keep_alive_handler = NULL,
-       .new_connection_handler = rtt_new_connection,
-       .input_handler = rtt_input,
-       .connection_closed_handler = rtt_connection_closed,
-       .keep_client_alive_handler = NULL,
+       .new_connection_during_keep_alive = NULL,
+       .new_connection = rtt_new_connection,
+       .input = rtt_input,
+       .service_dtor = NULL,
+       .connection_closed = rtt_connection_closed,
+       .keep_client_alive = NULL,
 };
 
 COMMAND_HANDLER(handle_rtt_start_command)
diff --git a/src/server/server.c b/src/server/server.c
index 0b957836d3..a943ace6cb 100644
--- a/src/server/server.c
+++ b/src/server/server.c
@@ -89,7 +89,7 @@ static int add_connection(struct service *service, struct 
command_context *cmd_c
                        sizeof(int));                   /* length of option 
value */
 
                LOG_INFO("accepting '%s' connection on tcp/%s", service->name, 
service->port);
-               retval = service->new_connection(c);
+               retval = service->driver->new_connection(c);
                if (retval != ERROR_OK) {
                        close_socket(c->fd);
                        LOG_ERROR("attempted '%s' connection rejected", 
service->name);
@@ -110,7 +110,7 @@ static int add_connection(struct service *service, struct 
command_context *cmd_c
                service->fd = -1;
 
                LOG_INFO("accepting '%s' connection from pipe", service->name);
-               retval = service->new_connection(c);
+               retval = service->driver->new_connection(c);
                if (retval != ERROR_OK) {
                        LOG_ERROR("attempted '%s' connection rejected", 
service->name);
                        command_done(c->cmd_ctx);
@@ -133,7 +133,7 @@ static int add_connection(struct service *service, struct 
command_context *cmd_c
                }
 
                LOG_INFO("accepting '%s' connection from pipe %s", 
service->name, service->port);
-               retval = service->new_connection(c);
+               retval = service->driver->new_connection(c);
                if (retval != ERROR_OK) {
                        LOG_ERROR("attempted '%s' connection rejected", 
service->name);
                        command_done(c->cmd_ctx);
@@ -161,8 +161,8 @@ static int remove_connection(struct service *service, 
struct connection *connect
        /* find connection */
        while ((c = *p)) {
                if (c->fd == connection->fd) {
-                       if (service->connection_closed)
-                               service->connection_closed(c);
+                       if (service->driver->connection_closed)
+                               service->driver->connection_closed(c);
                        if (service->type == CONNECTION_TCP)
                                close_socket(c->fd);
                        else if (service->type == CONNECTION_PIPE) {
@@ -195,9 +195,8 @@ static void free_service(struct service *c)
                close(c->fd);
        if (c->type == CONNECTION_TCP && c->fd != -1)
                close_socket(c->fd);
-       if (c->service_dtor)
-               c->service_dtor(c);
-       free(c->name);
+       if (c->driver->service_dtor)
+               c->driver->service_dtor(c);
        free(c->port);
        free(c->priv);
        free(c);
@@ -216,21 +215,16 @@ int add_service(const struct service_driver *driver, 
const char *port,
                return ERROR_FAIL;
        }
 
-       c->name = strdup(driver->name);
+       c->name = driver->name;
+       c->driver = driver;
        c->port = strdup(port);
        c->max_connections = 1; /* Only TCP/IP ports can support more than one 
connection */
        c->fd = -1;
        c->connections = NULL;
-       c->new_connection_during_keep_alive = 
driver->new_connection_during_keep_alive_handler;
-       c->new_connection = driver->new_connection_handler;
-       c->input = driver->input_handler;
-       c->connection_closed = driver->connection_closed_handler;
-       c->keep_client_alive = driver->keep_client_alive_handler;
-       c->service_dtor = driver->service_dtor_handler;
        c->priv = priv;
        c->next = NULL;
 
-       if (!c->name || !c->port) {
+       if (!c->port) {
                LOG_ERROR("Out of memory");
                goto error;
        }
@@ -352,7 +346,6 @@ int add_service(const struct service_driver *driver, const 
char *port,
 error:
        // Only free() what has been locally allocated
        free(c->port);
-       free(c->name);
        free(c);
 
        return ERROR_FAIL;
@@ -423,9 +416,9 @@ static int remove_services(void)
 void server_keep_clients_alive(void)
 {
        for (struct service *s = services; s; s = s->next)
-               if (s->keep_client_alive)
+               if (s->driver->keep_client_alive)
                        for (struct connection *c = s->connections; c; c = 
c->next)
-                               s->keep_client_alive(c);
+                               s->driver->keep_client_alive(c);
 }
 
 int server_loop(struct command_context *command_context)
@@ -571,7 +564,7 @@ int server_loop(struct command_context *command_context)
 
                                for (c = service->connections; c; ) {
                                        if ((c->fd >= 0 && FD_ISSET(c->fd, 
&read_fds)) || c->input_pending) {
-                                               retval = service->input(c);
+                                               retval = 
service->driver->input(c);
                                                if (retval != ERROR_OK) {
                                                        struct connection *next 
= c->next;
                                                        if (service->type == 
CONNECTION_PIPE ||
diff --git a/src/server/server.h b/src/server/server.h
index 393dba7691..8ba59127ab 100644
--- a/src/server/server.h
+++ b/src/server/server.h
@@ -48,25 +48,26 @@ struct service_driver {
        /** the name of the server */
        const char *name;
        /** optional minimal setup to accept a connection during keep-alive */
-       int (*new_connection_during_keep_alive_handler)(struct connection 
*connection);
+       int (*new_connection_during_keep_alive)(struct connection *connection);
        /**
         * complete code to accept a new connection.
-        * If 'new_connection_during_keep_alive_handler' above is present, this 
can be
+        * If 'new_connection_during_keep_alive' above is present, this can be
         * either called alone during the server_loop, or after the function 
above.
         * Check the implementation in gdb_server.
         * */
-       int (*new_connection_handler)(struct connection *connection);
+       int (*new_connection)(struct connection *connection);
        /** callback to handle incoming data */
-       int (*input_handler)(struct connection *connection);
-       void (*service_dtor_handler)(struct service *service);
+       int (*input)(struct connection *connection);
+       void (*service_dtor)(struct service *service);
        /** callback to tear down the connection */
-       int (*connection_closed_handler)(struct connection *connection);
+       int (*connection_closed)(struct connection *connection);
        /** called periodically to send keep-alive messages on the connection */
-       void (*keep_client_alive_handler)(struct connection *connection);
+       void (*keep_client_alive)(struct connection *connection);
 };
 
 struct service {
-       char *name;
+       const char *name;
+       const struct service_driver *driver;
        enum connection_type type;
        char *port;
        unsigned short portnumber;
@@ -74,12 +75,6 @@ struct service {
        struct sockaddr_in sin;
        int max_connections;
        struct connection *connections;
-       int (*new_connection_during_keep_alive)(struct connection *connection);
-       int (*new_connection)(struct connection *connection);
-       int (*input)(struct connection *connection);
-       void (*service_dtor)(struct service *service);
-       int (*connection_closed)(struct connection *connection);
-       void (*keep_client_alive)(struct connection *connection);
        void *priv;
        struct service *next;
 };
diff --git a/src/server/tcl_server.c b/src/server/tcl_server.c
index 16cc55e29b..42fce8f752 100644
--- a/src/server/tcl_server.c
+++ b/src/server/tcl_server.c
@@ -267,11 +267,12 @@ static int tcl_closed(struct connection *connection)
 
 static const struct service_driver tcl_service_driver = {
        .name = "tcl",
-       .new_connection_during_keep_alive_handler = NULL,
-       .new_connection_handler = tcl_new_connection,
-       .input_handler = tcl_input,
-       .connection_closed_handler = tcl_closed,
-       .keep_client_alive_handler = NULL,
+       .new_connection_during_keep_alive = NULL,
+       .new_connection = tcl_new_connection,
+       .input = tcl_input,
+       .service_dtor = NULL,
+       .connection_closed = tcl_closed,
+       .keep_client_alive = NULL,
 };
 
 int tcl_init(void)
diff --git a/src/server/telnet_server.c b/src/server/telnet_server.c
index 3634a2a592..6dff1e1c44 100644
--- a/src/server/telnet_server.c
+++ b/src/server/telnet_server.c
@@ -932,11 +932,12 @@ static int telnet_connection_closed(struct connection 
*connection)
 
 static const struct service_driver telnet_service_driver = {
        .name = "telnet",
-       .new_connection_during_keep_alive_handler = NULL,
-       .new_connection_handler = telnet_new_connection,
-       .input_handler = telnet_input,
-       .connection_closed_handler = telnet_connection_closed,
-       .keep_client_alive_handler = NULL,
+       .new_connection_during_keep_alive = NULL,
+       .new_connection = telnet_new_connection,
+       .input = telnet_input,
+       .service_dtor = NULL,
+       .connection_closed = telnet_connection_closed,
+       .keep_client_alive = NULL,
 };
 
 int telnet_init(char *banner)
diff --git a/src/target/arm_tpiu_swo.c b/src/target/arm_tpiu_swo.c
index 715b1c962c..fc84060fd8 100644
--- a/src/target/arm_tpiu_swo.c
+++ b/src/target/arm_tpiu_swo.c
@@ -598,11 +598,12 @@ static int wrap_read_u32(struct target *target, struct 
adiv5_ap *tpiu_ap,
 
 static const struct service_driver arm_tpiu_swo_service_driver = {
        .name = "tpiu_swo_trace",
-       .new_connection_during_keep_alive_handler = NULL,
-       .new_connection_handler = arm_tpiu_swo_service_new_connection,
-       .input_handler = arm_tpiu_swo_service_input,
-       .connection_closed_handler = arm_tpiu_swo_service_connection_closed,
-       .keep_client_alive_handler = NULL,
+       .new_connection_during_keep_alive = NULL,
+       .new_connection = arm_tpiu_swo_service_new_connection,
+       .input = arm_tpiu_swo_service_input,
+       .service_dtor = NULL,
+       .connection_closed = arm_tpiu_swo_service_connection_closed,
+       .keep_client_alive = NULL,
 };
 
 COMMAND_HANDLER(handle_arm_tpiu_swo_enable)
diff --git a/src/target/openrisc/jsp_server.c b/src/target/openrisc/jsp_server.c
index 60cbb49834..5369e86307 100644
--- a/src/target/openrisc/jsp_server.c
+++ b/src/target/openrisc/jsp_server.c
@@ -185,11 +185,12 @@ static int jsp_connection_closed(struct connection 
*connection)
 
 static const struct service_driver jsp_service_driver = {
        .name = "jsp",
-       .new_connection_during_keep_alive_handler = NULL,
-       .new_connection_handler = jsp_new_connection,
-       .input_handler = jsp_input,
-       .connection_closed_handler = jsp_connection_closed,
-       .keep_client_alive_handler = NULL,
+       .new_connection_during_keep_alive = NULL,
+       .new_connection = jsp_new_connection,
+       .input = jsp_input,
+       .service_dtor = NULL,
+       .connection_closed = jsp_connection_closed,
+       .keep_client_alive = NULL,
 };
 
 int jsp_init(struct or1k_jtag *jtag_info, char *banner)
diff --git a/src/target/semihosting_common.c b/src/target/semihosting_common.c
index 345e542c3c..d4435aa2a5 100644
--- a/src/target/semihosting_common.c
+++ b/src/target/semihosting_common.c
@@ -1821,12 +1821,12 @@ static void semihosting_tcp_close_cnx(struct 
semihosting *semihosting)
 
 static const struct service_driver semihosting_service_driver = {
        .name = "semihosting",
-       .new_connection_during_keep_alive_handler = NULL,
-       .new_connection_handler = semihosting_service_new_connection_handler,
-       .input_handler = semihosting_service_input_handler,
-       .service_dtor_handler = semihosting_service_dtor_handler,
-       .connection_closed_handler = NULL,
-       .keep_client_alive_handler = NULL,
+       .new_connection_during_keep_alive = NULL,
+       .new_connection = semihosting_service_new_connection_handler,
+       .input = semihosting_service_input_handler,
+       .service_dtor = semihosting_service_dtor_handler,
+       .connection_closed = NULL,
+       .keep_client_alive = NULL,
 };
 
 /* -------------------------------------------------------------------------

-- 

Reply via email to