summaryrefslogtreecommitdiff
path: root/apps/misc.c
diff options
context:
space:
mode:
authorMiika Pekkarinen <miipekk@ihme.org>2006-10-21 20:37:33 +0000
committerMiika Pekkarinen <miipekk@ihme.org>2006-10-21 20:37:33 +0000
commita1ac7434534240f9ce88054028a77466c6e61c7c (patch)
treeb2d4fc2f7d8fc0dbea12607ee93df8f2320859a7 /apps/misc.c
parent593b552486c6502d415f9f31fbaff871a0248cdc (diff)
Implement fast_readline as a function and use it for tagtree also.
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@11301 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'apps/misc.c')
-rw-r--r--apps/misc.c47
1 files changed, 47 insertions, 0 deletions
diff --git a/apps/misc.c b/apps/misc.c
index 4be9e43fd9..0936e85569 100644
--- a/apps/misc.c
+++ b/apps/misc.c
@@ -217,6 +217,53 @@ int read_line(int fd, char* buffer, int buffer_size)
return errno ? -1 : num_read;
}
+/* Performance optimized version of the previous function. */
+int fast_readline(int fd, char *buf, int buf_size, void *parameters,
+ int (*callback)(int n, const char *buf, void *parameters))
+{
+ char *p, *next;
+ int rc, pos = 0;
+ int count = 0;
+
+ while ( 1 )
+ {
+ next = NULL;
+
+ rc = read(fd, &buf[pos], buf_size - pos - 1);
+ if (rc >= 0)
+ buf[pos+rc] = '\0';
+
+ if ( (p = strchr(buf, '\r')) != NULL)
+ {
+ *p = '\0';
+ next = ++p;
+ }
+ else
+ p = buf;
+
+ if ( (p = strchr(p, '\n')) != NULL)
+ {
+ *p = '\0';
+ next = ++p;
+ }
+
+ rc = callback(count, buf, parameters);
+ if (rc < 0)
+ return rc;
+
+ count++;
+ if (next)
+ {
+ pos = buf_size - ((long)next - (long)buf) - 1;
+ memmove(buf, next, pos);
+ }
+ else
+ break ;
+ }
+
+ return 0;
+}
+
#ifdef HAVE_LCD_BITMAP
#if LCD_DEPTH == 16