pespin has uploaded this change for review. ( 
https://gerrit.osmocom.org/c/osmo-pcap/+/39303?usp=email )


Change subject: server: Avoid lseek syscall on every packet write to pcap file
......................................................................

server: Avoid lseek syscall on every packet write to pcap file

Instead of requesting the current size to the OS, keep track of the
amount of bytes stored in conn->wr_offset, and check agains that value
when we want to write new data to the file.
This should remove quite a lot of oeverhead when lots of traffic is
being handled.

Change-Id: I437eaca982d65d0f06e7d24863875f85267f0e44
---
M include/osmo-pcap/osmo_pcap_server.h
M src/osmo_server_core.c
2 files changed, 22 insertions(+), 16 deletions(-)



  git pull ssh://gerrit.osmocom.org:29418/osmo-pcap refs/changes/03/39303/1

diff --git a/include/osmo-pcap/osmo_pcap_server.h 
b/include/osmo-pcap/osmo_pcap_server.h
index 9a44fce..5d21c64 100644
--- a/include/osmo-pcap/osmo_pcap_server.h
+++ b/include/osmo-pcap/osmo_pcap_server.h
@@ -87,6 +87,8 @@
        int local_fd;
        /* canonicalized absolute pathname of pcap file we write to */
        char *curr_filename;
+       /* Current write offset of the file we write to (local_fd) */
+       off_t wr_offset;

        /* pcap stuff */
        enum osmo_pcap_fmt file_fmt;
diff --git a/src/osmo_server_core.c b/src/osmo_server_core.c
index b35d2b7..cc834a2 100644
--- a/src/osmo_server_core.c
+++ b/src/osmo_server_core.c
@@ -308,12 +308,17 @@
        talloc_free(curr_filename_cpy_dname);
 }

+static void close_local_fd(struct osmo_pcap_conn *conn)
+{
+       close(conn->local_fd);
+       conn->local_fd = -1;
+       conn->wr_offset = 0;
+}
+
 void osmo_pcap_conn_close_trace(struct osmo_pcap_conn *conn)
 {
-       if (conn->local_fd >= 0) {
-               close(conn->local_fd);
-               conn->local_fd = -1;
-       }
+       if (conn->local_fd >= 0)
+               close_local_fd(conn);

        move_completed_trace_if_needed(conn);

@@ -342,7 +347,7 @@
 /* Update conn->last_write if needed. This field is used to keep the last time
  * period where we wrote to the pcap file. Once a new write period (based on
  * rotation VTY config) is detected, the pcap file we write to is rotated. */
-static void update_last_write(struct osmo_pcap_conn *conn, time_t now)
+static void update_last_write(struct osmo_pcap_conn *conn, time_t now, size_t 
len)
 {
        time_t last = mktime(&conn->last_write);

@@ -352,6 +357,8 @@
         * using the current one. */
        if (now > last)
                localtime_r(&now, &conn->last_write);
+
+       conn->wr_offset += len;
 }

 void osmo_pcap_conn_restart_trace(struct osmo_pcap_conn *conn)
@@ -365,7 +372,7 @@

        /* omit any storing/creation of the file */
        if (!conn->store) {
-               update_last_write(conn, now);
+               update_last_write(conn, now, 0);
                talloc_free(conn->curr_filename);
                conn->curr_filename = NULL;
                return;
@@ -395,28 +402,25 @@
                     conn->curr_filename, strerror(errno));
                return;
        }
+       conn->wr_offset = 0;

        rc = write(conn->local_fd, conn->file_hdr, conn->file_hdr_len);
        if (rc != conn->file_hdr_len) {
                LOGP(DSERVER, LOGL_ERROR, "Failed to write the header: %d\n", 
errno);
-               close(conn->local_fd);
-               conn->local_fd = -1;
+               close_local_fd(conn);
                return;
        }
-
-       update_last_write(conn, now);
+       update_last_write(conn, now, rc);
 }

 /* Returns true if pcap was re-opened */
 static bool check_restart_pcap_max_size(struct osmo_pcap_conn *conn, size_t 
data_len)
 {
-       off_t cur;
-
        if (!pcap_server->max_size_enabled)
                return false;
-       cur = lseek(conn->local_fd, 0, SEEK_CUR);
-       if (cur + data_len <= conn->server->max_size)
+       if (conn->wr_offset + data_len <= conn->server->max_size)
                return false;
+
        LOGP(DSERVER, LOGL_NOTICE, "Rolling over file for %s (max-size)\n", 
conn->name);
        osmo_pcap_conn_restart_trace(conn);
        return true;
@@ -554,7 +558,7 @@
        zmq_send_client_data(conn, data, len);

        if (!conn->store) {
-               update_last_write(conn, now);
+               update_last_write(conn, now, 0);
                return 0;
        }

@@ -567,11 +571,11 @@
        if (!check_restart_pcap_max_size(conn, len))
                check_restart_pcap_localtime(conn, now);

-       update_last_write(conn, now);
        rc = write(conn->local_fd, data, len);
        if (rc != len) {
                LOGP(DSERVER, LOGL_ERROR, "Failed to write for %s\n", 
conn->name);
                return -1;
        }
+       update_last_write(conn, now, rc);
        return 0;
 }

--
To view, visit https://gerrit.osmocom.org/c/osmo-pcap/+/39303?usp=email
To unsubscribe, or for help writing mail filters, visit 
https://gerrit.osmocom.org/settings?usp=email

Gerrit-MessageType: newchange
Gerrit-Project: osmo-pcap
Gerrit-Branch: master
Gerrit-Change-Id: I437eaca982d65d0f06e7d24863875f85267f0e44
Gerrit-Change-Number: 39303
Gerrit-PatchSet: 1
Gerrit-Owner: pespin <[email protected]>

Reply via email to