diff options
author | Ekaitz Zarraga <ekaitz@elenq.tech> | 2024-03-02 23:44:28 +0100 |
---|---|---|
committer | Ekaitz Zarraga <ekaitz@elenq.tech> | 2024-03-02 23:44:28 +0100 |
commit | d789313bd0a1f596ba73224777a017ac39ecbb3b (patch) | |
tree | 84f1dc3f6a4a36a20a55baab2ccb6bbcd6ea0c93 | |
parent | 13b990a49dc9f18c17110f2c6d9f3c8d2e324851 (diff) |
piece-table: index and start with insert
-rw-r--r-- | src/piece-table.c | 55 | ||||
-rw-r--r-- | src/piece-table.h | 14 |
2 files changed, 61 insertions, 8 deletions
diff --git a/src/piece-table.c b/src/piece-table.c index 490950b..be9f1b2 100644 --- a/src/piece-table.c +++ b/src/piece-table.c @@ -1,3 +1,4 @@ +#include <assert.h> #include "piece-table.h" static piece *make_piece() { @@ -39,6 +40,16 @@ bool init_piece_table(piece_table *pt, char *orig) { return true; } + +static void free_piece_list(piece *p) { + piece *cur, *next; + assert(p != NULL); + for ( cur = p; cur != p; cur = next ) { + next = cur->next; + free( cur ); + } +} + void free_piece_table(piece_table *pt) { free_growable_buffer(&pt->add); free_fixed_buffer(&pt->orig); @@ -49,6 +60,48 @@ void free_piece_table(piece_table *pt) { pt->length = 0; } -void free_piece_list(piece *pt) { + +static void find_piece_by_pos(piece_table *pt, size_t pos) { + piece *cur; + assert(pos < pt->length); + if ( pos >= pt->cached_offset ) { + /* Search forward */ + for ( cur = pt->cached; ; cur = cur->next ) { + if ( pt->cached_offset + pt->length > pos ) { + pt->cached = cur; + assert(pt->cached != pt->sentinel); + return; + } + pt->cached_offset += cur->length; + } + } else { + /* Search backwards */ + for ( cur = pt->cached->prev; ; cur = cur->prev ) { + pt->cached_offset -= cur->length; + if ( pt->cached_offset < pos ) { + pt->cached = cur; + assert(pt->cached != pt->sentinel); + return; + } + } + } +} + +char index_piece_table(piece_table *pt, size_t pos) { + assert(pos < pt->length); + find_piece_by_pos(pt, pos); + return pt->cached->start[pos - pt->cached_offset]; +} + +void insert_piece_table(piece_table *pt, char val, size_t pos) { + /* At the moment inserts only one char */ + append_growable_buffer(&pt->add, &val, 1); + + find_piece_by_pos(pt, pos); + // TODO } + +void delete_piece_table(piece_table *pt, size_t pos, size_t len) { + +} diff --git a/src/piece-table.h b/src/piece-table.h index 94ab072..c053069 100644 --- a/src/piece-table.h +++ b/src/piece-table.h @@ -5,14 +5,12 @@ #include <stddef.h> #include "buffer.h" -struct piece { +typedef struct _piece { char *start; size_t length; - struct piece *next; - struct piece *prev; -}; - -typedef struct piece piece; + struct _piece *next; + struct _piece *prev; +} piece; typedef struct { fixed_buffer orig; @@ -27,6 +25,8 @@ typedef struct { bool init_piece_table(piece_table *pt, char *orig); void free_piece_table(piece_table *pt); -void free_piece_list(piece *pt); +char index_piece_table(piece_table *pt, size_t pos); +void insert_piece_table(piece_table *pt, char val, size_t pos); +void delete_piece_table(piece_table *pt, size_t pos, size_t len); #endif // PIECE_TABLE_H |