src/buffer.c

Fri, 23 May 2025 12:44:24 +0200

author
Mike Becker <universe@uap-core.de>
date
Fri, 23 May 2025 12:44:24 +0200
changeset 1327
ed75dc1db503
parent 1319
aa1f580f8f59
permissions
-rw-r--r--

make test-compile depend on both static and shared

the shared lib is not needed for the tests,
but when run with coverage, gcov will be confused
when outdated line information is available from
a previous shared build

483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
1 /*
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
2 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
3 *
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
4 * Copyright 2021 Mike Becker, Olaf Wintermann All rights reserved.
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
5 *
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
6 * Redistribution and use in source and binary forms, with or without
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
7 * modification, are permitted provided that the following conditions are met:
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
8 *
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
9 * 1. Redistributions of source code must retain the above copyright
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
10 * notice, this list of conditions and the following disclaimer.
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
11 *
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
12 * 2. Redistributions in binary form must reproduce the above copyright
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
13 * notice, this list of conditions and the following disclaimer in the
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
14 * documentation and/or other materials provided with the distribution.
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
15 *
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
17 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
20 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
23 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
24 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
26 * POSSIBILITY OF SUCH DAMAGE.
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
27 */
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
28
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
29 #include "cx/buffer.h"
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
30
530
e866516cac17 #170 first buffer tests
Mike Becker <universe@uap-core.de>
parents: 529
diff changeset
31 #include <stdio.h>
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
32 #include <string.h>
1040
1ecf4dbbc60c add some more overflow treatment and make sure to set errno properly
Mike Becker <universe@uap-core.de>
parents: 1030
diff changeset
33 #include <errno.h>
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
34
1292
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
35 #ifdef _WIN32
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
36 #include <Windows.h>
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
37 #include <sysinfoapi.h>
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
38 static unsigned long system_page_size() {
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
39 static unsigned long ps = 0;
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
40 if (ps == 0) {
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
41 SYSTEM_INFO sysinfo;
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
42 GetSystemInfo(&sysinfo);
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
43 ps = sysinfo.dwPageSize;
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
44 }
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
45 return ps;
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
46 }
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
47 #define SYSTEM_PAGE_SIZE system_page_size()
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
48 #else
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
49 #include <unistd.h>
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
50 #define SYSTEM_PAGE_SIZE sysconf(_SC_PAGESIZE)
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
51 #endif
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
52
1028
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
53 static int buffer_copy_on_write(CxBuffer* buffer) {
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
54 if (0 == (buffer->flags & CX_BUFFER_COPY_ON_WRITE)) return 0;
1028
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
55 void *newspace = cxMalloc(buffer->allocator, buffer->capacity);
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
56 if (NULL == newspace) return -1;
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
57 memcpy(newspace, buffer->space, buffer->size);
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
58 buffer->space = newspace;
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
59 buffer->flags &= ~CX_BUFFER_COPY_ON_WRITE;
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
60 buffer->flags |= CX_BUFFER_FREE_CONTENTS;
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
61 return 0;
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
62 }
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
63
501
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
64 int cxBufferInit(
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
65 CxBuffer *buffer,
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
66 void *space,
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
67 size_t capacity,
890
54565fd74e74 move all const keywords to the west - fixes #426
Mike Becker <universe@uap-core.de>
parents: 761
diff changeset
68 const CxAllocator *allocator,
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
69 int flags
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
70 ) {
989
8aa57a7fecc4 improve consistency for allocator arguments - fixes #485
Mike Becker <universe@uap-core.de>
parents: 985
diff changeset
71 if (allocator == NULL) {
8aa57a7fecc4 improve consistency for allocator arguments - fixes #485
Mike Becker <universe@uap-core.de>
parents: 985
diff changeset
72 allocator = cxDefaultAllocator;
8aa57a7fecc4 improve consistency for allocator arguments - fixes #485
Mike Becker <universe@uap-core.de>
parents: 985
diff changeset
73 }
1028
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
74 if (flags & CX_BUFFER_COPY_ON_EXTEND) {
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
75 flags |= CX_BUFFER_AUTO_EXTEND;
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
76 }
501
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
77 buffer->allocator = allocator;
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
78 buffer->flags = flags;
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
79 if (!space) {
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
80 buffer->bytes = cxMalloc(allocator, capacity);
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
81 if (buffer->bytes == NULL) {
1065
6eb7b54975ee improve coverage metrics
Mike Becker <universe@uap-core.de>
parents: 1040
diff changeset
82 return -1; // LCOV_EXCL_LINE
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
83 }
501
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
84 buffer->flags |= CX_BUFFER_FREE_CONTENTS;
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
85 } else {
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
86 buffer->bytes = space;
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
87 }
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
88 buffer->capacity = capacity;
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
89 buffer->size = 0;
539
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
90 buffer->pos = 0;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
91
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
92 buffer->flush = NULL;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
93
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
94 return 0;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
95 }
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
96
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
97 int cxBufferEnableFlushing(
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
98 CxBuffer *buffer,
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
99 CxBufferFlushConfig config
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
100 ) {
1319
aa1f580f8f59 add convenience macros for using the default allocator - relates to #669
Mike Becker <universe@uap-core.de>
parents: 1318
diff changeset
101 buffer->flush = cxMallocDefault(sizeof(CxBufferFlushConfig));
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
102 if (buffer->flush == NULL) return -1; // LCOV_EXCL_LINE
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
103 memcpy(buffer->flush, &config, sizeof(CxBufferFlushConfig));
501
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
104 return 0;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
105 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
106
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
107 void cxBufferDestroy(CxBuffer *buffer) {
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
108 if (buffer->flags & CX_BUFFER_FREE_CONTENTS) {
501
9a08f5e515cc add allocator support to CxBuffer
Mike Becker <universe@uap-core.de>
parents: 500
diff changeset
109 cxFree(buffer->allocator, buffer->bytes);
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
110 }
1319
aa1f580f8f59 add convenience macros for using the default allocator - relates to #669
Mike Becker <universe@uap-core.de>
parents: 1318
diff changeset
111 cxFreeDefault(buffer->flush);
1030
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
112 memset(buffer, 0, sizeof(CxBuffer));
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
113 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
114
683
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
115 CxBuffer *cxBufferCreate(
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
116 void *space,
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
117 size_t capacity,
890
54565fd74e74 move all const keywords to the west - fixes #426
Mike Becker <universe@uap-core.de>
parents: 761
diff changeset
118 const CxAllocator *allocator,
683
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
119 int flags
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
120 ) {
989
8aa57a7fecc4 improve consistency for allocator arguments - fixes #485
Mike Becker <universe@uap-core.de>
parents: 985
diff changeset
121 if (allocator == NULL) {
8aa57a7fecc4 improve consistency for allocator arguments - fixes #485
Mike Becker <universe@uap-core.de>
parents: 985
diff changeset
122 allocator = cxDefaultAllocator;
8aa57a7fecc4 improve consistency for allocator arguments - fixes #485
Mike Becker <universe@uap-core.de>
parents: 985
diff changeset
123 }
683
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
124 CxBuffer *buf = cxMalloc(allocator, sizeof(CxBuffer));
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
125 if (buf == NULL) return NULL;
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
126 if (0 == cxBufferInit(buf, space, capacity, allocator, flags)) {
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
127 return buf;
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
128 } else {
1065
6eb7b54975ee improve coverage metrics
Mike Becker <universe@uap-core.de>
parents: 1040
diff changeset
129 // LCOV_EXCL_START
683
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
130 cxFree(allocator, buf);
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
131 return NULL;
1065
6eb7b54975ee improve coverage metrics
Mike Becker <universe@uap-core.de>
parents: 1040
diff changeset
132 // LCOV_EXCL_STOP
683
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
133 }
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
134 }
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
135
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
136 void cxBufferFree(CxBuffer *buffer) {
985
68754c7de906 major refactoring of attributes
Mike Becker <universe@uap-core.de>
parents: 970
diff changeset
137 if (buffer == NULL) return;
1030
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
138 const CxAllocator *allocator = buffer->allocator;
991
ec49db06dae0 cxBufferFree() now calls cxBufferDestroy()
Mike Becker <universe@uap-core.de>
parents: 989
diff changeset
139 cxBufferDestroy(buffer);
1030
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
140 cxFree(allocator, buffer);
683
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
141 }
aa0d09f2d81c add convenience functions for allocating a buffer on the heap
Mike Becker <universe@uap-core.de>
parents: 673
diff changeset
142
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
143 int cxBufferSeek(
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
144 CxBuffer *buffer,
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
145 off_t offset,
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
146 int whence
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
147 ) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
148 size_t npos;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
149 switch (whence) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
150 case SEEK_CUR:
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
151 npos = buffer->pos;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
152 break;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
153 case SEEK_END:
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
154 npos = buffer->size;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
155 break;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
156 case SEEK_SET:
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
157 npos = 0;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
158 break;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
159 default:
1259
7bc999fe285d more documentation for buffer.h + set errno in cxBufferSeek() on invalid whence argument
Mike Becker <universe@uap-core.de>
parents: 1138
diff changeset
160 errno = EINVAL;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
161 return -1;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
162 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
163
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
164 size_t opos = npos;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
165 npos += offset;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
166
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
167 if ((offset > 0 && npos < opos) || (offset < 0 && npos > opos)) {
1288
b41ad5d9bcbf fixes errno value after failing cxBufferSeek() to be consistently EINVAL
Mike Becker <universe@uap-core.de>
parents: 1284
diff changeset
168 // to be compliant with fseek() specification
b41ad5d9bcbf fixes errno value after failing cxBufferSeek() to be consistently EINVAL
Mike Becker <universe@uap-core.de>
parents: 1284
diff changeset
169 // we return EINVAL on underflow
b41ad5d9bcbf fixes errno value after failing cxBufferSeek() to be consistently EINVAL
Mike Becker <universe@uap-core.de>
parents: 1284
diff changeset
170 errno = EINVAL;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
171 return -1;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
172 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
173
1007
81b2986d2b04 fix that cxBufferSeek() cannot move pos past the end - fixes #523
Mike Becker <universe@uap-core.de>
parents: 1005
diff changeset
174 if (npos > buffer->size) {
1288
b41ad5d9bcbf fixes errno value after failing cxBufferSeek() to be consistently EINVAL
Mike Becker <universe@uap-core.de>
parents: 1284
diff changeset
175 // not compliant with fseek() specification
b41ad5d9bcbf fixes errno value after failing cxBufferSeek() to be consistently EINVAL
Mike Becker <universe@uap-core.de>
parents: 1284
diff changeset
176 // but this is the better behavior for CxBuffer
b41ad5d9bcbf fixes errno value after failing cxBufferSeek() to be consistently EINVAL
Mike Becker <universe@uap-core.de>
parents: 1284
diff changeset
177 errno = EINVAL;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
178 return -1;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
179 } else {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
180 buffer->pos = npos;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
181 return 0;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
182 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
183
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
184 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
185
529
814d51173f20 #171 const qualifier and nonnull attributes
Mike Becker <universe@uap-core.de>
parents: 501
diff changeset
186 void cxBufferClear(CxBuffer *buffer) {
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
187 if (0 == (buffer->flags & CX_BUFFER_COPY_ON_WRITE)) {
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
188 memset(buffer->bytes, 0, buffer->size);
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
189 }
529
814d51173f20 #171 const qualifier and nonnull attributes
Mike Becker <universe@uap-core.de>
parents: 501
diff changeset
190 buffer->size = 0;
814d51173f20 #171 const qualifier and nonnull attributes
Mike Becker <universe@uap-core.de>
parents: 501
diff changeset
191 buffer->pos = 0;
814d51173f20 #171 const qualifier and nonnull attributes
Mike Becker <universe@uap-core.de>
parents: 501
diff changeset
192 }
814d51173f20 #171 const qualifier and nonnull attributes
Mike Becker <universe@uap-core.de>
parents: 501
diff changeset
193
761
61d5197d612b add cxBufferReset() - resolves #338
Mike Becker <universe@uap-core.de>
parents: 683
diff changeset
194 void cxBufferReset(CxBuffer *buffer) {
61d5197d612b add cxBufferReset() - resolves #338
Mike Becker <universe@uap-core.de>
parents: 683
diff changeset
195 buffer->size = 0;
61d5197d612b add cxBufferReset() - resolves #338
Mike Becker <universe@uap-core.de>
parents: 683
diff changeset
196 buffer->pos = 0;
61d5197d612b add cxBufferReset() - resolves #338
Mike Becker <universe@uap-core.de>
parents: 683
diff changeset
197 }
61d5197d612b add cxBufferReset() - resolves #338
Mike Becker <universe@uap-core.de>
parents: 683
diff changeset
198
1004
d8044fd5005c make cxBufferEof() return a bool
Mike Becker <universe@uap-core.de>
parents: 991
diff changeset
199 bool cxBufferEof(const CxBuffer *buffer) {
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
200 return buffer->pos >= buffer->size;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
201 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
202
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
203 int cxBufferMinimumCapacity(
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
204 CxBuffer *buffer,
532
080c304ec176 fix cxBufferMinimumCapacity implementation still using additional_bytes
Mike Becker <universe@uap-core.de>
parents: 530
diff changeset
205 size_t newcap
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
206 ) {
532
080c304ec176 fix cxBufferMinimumCapacity implementation still using additional_bytes
Mike Becker <universe@uap-core.de>
parents: 530
diff changeset
207 if (newcap <= buffer->capacity) {
080c304ec176 fix cxBufferMinimumCapacity implementation still using additional_bytes
Mike Becker <universe@uap-core.de>
parents: 530
diff changeset
208 return 0;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
209 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
210
1292
1e7ee17777f4 add windows support for new buffer auto-extend strategy - relates to #641
Mike Becker <universe@uap-core.de>
parents: 1291
diff changeset
211 unsigned long pagesize = SYSTEM_PAGE_SIZE;
1291
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
212 // if page size is larger than 64 KB - for some reason - truncate to 64 KB
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
213 if (pagesize > 65536) pagesize = 65536;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
214 if (newcap < pagesize) {
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
215 // when smaller as one page, map to the next power of two
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
216 newcap--;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
217 newcap |= newcap >> 1;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
218 newcap |= newcap >> 2;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
219 newcap |= newcap >> 4;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
220 // last operation only needed for pages larger 4096 bytes
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
221 // but if/else would be more expensive than just doing this
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
222 newcap |= newcap >> 8;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
223 newcap++;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
224 } else {
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
225 // otherwise, map to a multiple of the page size
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
226 newcap -= newcap % pagesize;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
227 newcap += pagesize;
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
228 // note: if newcap is already page aligned,
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
229 // this gives a full additional page (which is good)
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
230 }
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
231
5942859fd76c new auto-extend strategy for CxBuffer - resolves #641
Mike Becker <universe@uap-core.de>
parents: 1290
diff changeset
232
1028
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
233 const int force_copy_flags = CX_BUFFER_COPY_ON_WRITE | CX_BUFFER_COPY_ON_EXTEND;
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
234 if (buffer->flags & force_copy_flags) {
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
235 void *newspace = cxMalloc(buffer->allocator, newcap);
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
236 if (NULL == newspace) return -1;
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
237 memcpy(newspace, buffer->space, buffer->size);
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
238 buffer->space = newspace;
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
239 buffer->capacity = newcap;
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
240 buffer->flags &= ~force_copy_flags;
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
241 buffer->flags |= CX_BUFFER_FREE_CONTENTS;
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
242 return 0;
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
243 } else if (cxReallocate(buffer->allocator,
536
cb9b9739055e #170 add cxBufferClear test
Mike Becker <universe@uap-core.de>
parents: 534
diff changeset
244 (void **) &buffer->bytes, newcap) == 0) {
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
245 buffer->capacity = newcap;
533
8d70ad8da899 do not implicitly zero freshly allocated memory
Mike Becker <universe@uap-core.de>
parents: 532
diff changeset
246 return 0;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
247 } else {
1065
6eb7b54975ee improve coverage metrics
Mike Becker <universe@uap-core.de>
parents: 1040
diff changeset
248 return -1; // LCOV_EXCL_LINE
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
249 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
250 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
251
1290
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
252 void cxBufferShrink(
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
253 CxBuffer *buffer,
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
254 size_t reserve
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
255 ) {
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
256 // Ensure buffer is in a reallocatable state
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
257 const int force_copy_flags = CX_BUFFER_COPY_ON_WRITE | CX_BUFFER_COPY_ON_EXTEND;
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
258 if (buffer->flags & force_copy_flags) {
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
259 // do nothing when we are not allowed to reallocate
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
260 return;
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
261 }
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
262
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
263 // calculate new capacity
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
264 size_t newCapacity = buffer->size + reserve;
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
265
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
266 // If new capacity is smaller than current capacity, resize the buffer
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
267 if (newCapacity < buffer->capacity) {
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
268 if (0 == cxReallocate(buffer->allocator, &buffer->bytes, newCapacity)) {
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
269 buffer->capacity = newCapacity;
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
270 }
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
271 }
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
272 }
4ac889e14211 adds cxBufferShrink() - resolves #626
Mike Becker <universe@uap-core.de>
parents: 1288
diff changeset
273
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
274 static size_t cx_buffer_flush_helper(
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
275 const CxBuffer *buffer,
1128
3672b89e606c fix stupid signature of the flush helper
Mike Becker <universe@uap-core.de>
parents: 1110
diff changeset
276 const unsigned char *src,
544
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
277 size_t size,
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
278 size_t nitems
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
279 ) {
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
280 // flush data from an arbitrary source
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
281 // does not need to be the buffer's contents
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
282 size_t max_items = buffer->flush->blksize / size;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
283 size_t fblocks = 0;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
284 size_t flushed_total = 0;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
285 while (nitems > 0 && fblocks < buffer->flush->blkmax) {
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
286 fblocks++;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
287 size_t items = nitems > max_items ? max_items : nitems;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
288 size_t flushed = buffer->flush->wfunc(
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
289 src, size, items, buffer->flush->target);
544
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
290 if (flushed > 0) {
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
291 flushed_total += flushed;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
292 src += flushed * size;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
293 nitems -= flushed;
544
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
294 } else {
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
295 // if no bytes can be flushed out anymore, we give up
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
296 break;
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
297 }
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
298 }
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
299 return flushed_total;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
300 }
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
301
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
302 static size_t cx_buffer_flush_impl(CxBuffer *buffer, size_t size) {
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
303 // flush the current contents of the buffer
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
304 unsigned char *space = buffer->bytes;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
305 size_t remaining = buffer->pos / size;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
306 size_t flushed_total = cx_buffer_flush_helper(
1128
3672b89e606c fix stupid signature of the flush helper
Mike Becker <universe@uap-core.de>
parents: 1110
diff changeset
307 buffer, space, size, remaining);
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
308
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
309 // shift the buffer left after flushing
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
310 // IMPORTANT: up to this point, copy on write must have been
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
311 // performed already, because we can't do error handling here
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
312 cxBufferShiftLeft(buffer, flushed_total*size);
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
313
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
314 return flushed_total;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
315 }
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
316
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
317 size_t cxBufferFlush(CxBuffer *buffer) {
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
318 if (buffer_copy_on_write(buffer)) return 0;
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
319 return cx_buffer_flush_impl(buffer, 1);
544
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
320 }
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
321
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
322 size_t cxBufferWrite(
890
54565fd74e74 move all const keywords to the west - fixes #426
Mike Becker <universe@uap-core.de>
parents: 761
diff changeset
323 const void *ptr,
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
324 size_t size,
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
325 size_t nitems,
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
326 CxBuffer *buffer
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
327 ) {
543
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
328 // optimize for easy case
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
329 if (size == 1 && (buffer->capacity - buffer->pos) >= nitems) {
1028
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
330 if (buffer_copy_on_write(buffer)) return 0;
543
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
331 memcpy(buffer->bytes + buffer->pos, ptr, nitems);
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
332 buffer->pos += nitems;
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
333 if (buffer->pos > buffer->size) {
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
334 buffer->size = buffer->pos;
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
335 }
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
336 return nitems;
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
337 }
7b9114030ca4 optimization for buffer write easy cases
Mike Becker <universe@uap-core.de>
parents: 542
diff changeset
338
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
339 size_t len, total_flushed = 0;
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
340 cx_buffer_write_retry:
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
341 if (cx_szmul(size, nitems, &len)) {
1040
1ecf4dbbc60c add some more overflow treatment and make sure to set errno properly
Mike Becker <universe@uap-core.de>
parents: 1030
diff changeset
342 errno = EOVERFLOW;
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
343 return total_flushed;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
344 }
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
345 if (buffer->pos > SIZE_MAX - len) {
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
346 errno = EOVERFLOW;
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
347 return total_flushed;
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
348 }
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
349
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
350 size_t required = buffer->pos + len;
539
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
351 bool perform_flush = false;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
352 if (required > buffer->capacity) {
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
353 if (buffer->flags & CX_BUFFER_AUTO_EXTEND) {
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
354 if (buffer->flush != NULL && required > buffer->flush->threshold) {
539
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
355 perform_flush = true;
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
356 } else {
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
357 if (cxBufferMinimumCapacity(buffer, required)) {
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
358 return total_flushed; // LCOV_EXCL_LINE
539
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
359 }
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
360 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
361 } else {
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
362 if (buffer->flush != NULL) {
539
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
363 perform_flush = true;
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
364 } else {
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
365 // truncate data, if we can neither extend nor flush
539
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
366 len = buffer->capacity - buffer->pos;
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
367 if (size > 1) {
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
368 len -= len % size;
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
369 }
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
370 nitems = len / size;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
371 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
372 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
373 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
374
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
375 // check here and not above because of possible truncation
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
376 if (len == 0) {
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
377 return total_flushed;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
378 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
379
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
380 // check if we need to copy
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
381 if (buffer_copy_on_write(buffer)) return 0;
544
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
382
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
383 // perform the operation
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
384 if (perform_flush) {
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
385 size_t items_flushed;
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
386 if (buffer->pos == 0) {
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
387 // if we don't have data in the buffer, but are instructed
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
388 // to flush, it means that we are supposed to relay the data
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
389 items_flushed = cx_buffer_flush_helper(buffer, ptr, size, nitems);
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
390 if (items_flushed == 0) {
1135
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
391 // we needed to relay data, but could not flush anything
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
392 // i.e. we have to give up to avoid endless trying
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
393 return 0;
544
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
394 }
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
395 nitems -= items_flushed;
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
396 total_flushed += items_flushed;
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
397 if (nitems > 0) {
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
398 ptr = ((unsigned char*)ptr) + items_flushed * size;
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
399 goto cx_buffer_write_retry;
1128
3672b89e606c fix stupid signature of the flush helper
Mike Becker <universe@uap-core.de>
parents: 1110
diff changeset
400 }
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
401 return total_flushed;
1110
a0e9be7ed131 re-implement flushing
Mike Becker <universe@uap-core.de>
parents: 1065
diff changeset
402 } else {
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
403 items_flushed = cx_buffer_flush_impl(buffer, size);
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
404 if (items_flushed == 0) {
1135
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
405 // flush target is full, let's try to truncate
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
406 size_t remaining_space;
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
407 if (buffer->flags & CX_BUFFER_AUTO_EXTEND) {
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
408 remaining_space = buffer->flush->threshold > buffer->pos
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
409 ? buffer->flush->threshold - buffer->pos
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
410 : 0;
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
411 } else {
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
412 remaining_space = buffer->capacity > buffer->pos
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
413 ? buffer->capacity - buffer->pos
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
414 : 0;
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
415 }
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
416 nitems = remaining_space / size;
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
417 if (nitems == 0) {
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
418 return total_flushed;
1135
f79415d974d3 add test case for flushing when target is full and fixes a bug related to that
Mike Becker <universe@uap-core.de>
parents: 1131
diff changeset
419 }
544
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
420 }
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
421 goto cx_buffer_write_retry;
544
2e73456e5f84 #184 untested implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 543
diff changeset
422 }
539
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
423 } else {
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
424 memcpy(buffer->bytes + buffer->pos, ptr, len);
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
425 buffer->pos += len;
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
426 if (buffer->pos > buffer->size) {
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
427 buffer->size = buffer->pos;
9cd98da9ee17 #184 start implementation of the flush feature
Mike Becker <universe@uap-core.de>
parents: 538
diff changeset
428 }
1138
29672c777a28 avoid recursion in cxBufferWrite() - fixes #567
Mike Becker <universe@uap-core.de>
parents: 1135
diff changeset
429 return total_flushed + nitems;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
430 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
431 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
432
1030
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
433 size_t cxBufferAppend(
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
434 const void *ptr,
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
435 size_t size,
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
436 size_t nitems,
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
437 CxBuffer *buffer
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
438 ) {
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
439 size_t pos = buffer->pos;
1131
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
440 size_t append_pos = buffer->size;
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
441 buffer->pos = append_pos;
1030
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
442 size_t written = cxBufferWrite(ptr, size, nitems, buffer);
1131
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
443 // the buffer might have been flushed
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
444 // we must compute a possible delta for the position
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
445 // expected: pos = append_pos + written
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
446 // -> if this is not the case, there is a delta
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
447 size_t delta = append_pos + written*size - buffer->pos;
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
448 if (delta > pos) {
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
449 buffer->pos = 0;
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
450 } else {
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
451 buffer->pos = pos - delta;
644f77f903b1 fix cxBufferAppend() not adjusting position after flush
Mike Becker <universe@uap-core.de>
parents: 1128
diff changeset
452 }
1030
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
453 return written;
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
454 }
06091e067bee add cxBufferAppend() - fixes #534
Mike Becker <universe@uap-core.de>
parents: 1028
diff changeset
455
538
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
456 int cxBufferPut(
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
457 CxBuffer *buffer,
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
458 int c
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
459 ) {
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
460 c &= 0xFF;
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
461 unsigned char const ch = c;
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
462 if (cxBufferWrite(&ch, 1, 1, buffer) == 1) {
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
463 return c;
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
464 } else {
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
465 return EOF;
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
466 }
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
467 }
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
468
1005
67fa386ce600 add cxBufferTerminate()
Mike Becker <universe@uap-core.de>
parents: 1004
diff changeset
469 int cxBufferTerminate(CxBuffer *buffer) {
1284
b2103354baed fix implementation of cxBufferTerminate() - fixes #631
Mike Becker <universe@uap-core.de>
parents: 1259
diff changeset
470 if (0 == cxBufferPut(buffer, 0)) {
b2103354baed fix implementation of cxBufferTerminate() - fixes #631
Mike Becker <universe@uap-core.de>
parents: 1259
diff changeset
471 buffer->size = buffer->pos - 1;
1005
67fa386ce600 add cxBufferTerminate()
Mike Becker <universe@uap-core.de>
parents: 1004
diff changeset
472 return 0;
67fa386ce600 add cxBufferTerminate()
Mike Becker <universe@uap-core.de>
parents: 1004
diff changeset
473 } else {
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
474 return -1;
1005
67fa386ce600 add cxBufferTerminate()
Mike Becker <universe@uap-core.de>
parents: 1004
diff changeset
475 }
67fa386ce600 add cxBufferTerminate()
Mike Becker <universe@uap-core.de>
parents: 1004
diff changeset
476 }
67fa386ce600 add cxBufferTerminate()
Mike Becker <universe@uap-core.de>
parents: 1004
diff changeset
477
538
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
478 size_t cxBufferPutString(
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
479 CxBuffer *buffer,
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
480 const char *str
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
481 ) {
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
482 return cxBufferWrite(str, 1, strlen(str), buffer);
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
483 }
2cfbcbe86a7c #170 first basic write tests
Mike Becker <universe@uap-core.de>
parents: 536
diff changeset
484
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
485 size_t cxBufferRead(
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
486 void *ptr,
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
487 size_t size,
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
488 size_t nitems,
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
489 CxBuffer *buffer
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
490 ) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
491 size_t len;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
492 if (cx_szmul(size, nitems, &len)) {
1040
1ecf4dbbc60c add some more overflow treatment and make sure to set errno properly
Mike Becker <universe@uap-core.de>
parents: 1030
diff changeset
493 errno = EOVERFLOW;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
494 return 0;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
495 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
496 if (buffer->pos + len > buffer->size) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
497 len = buffer->size - buffer->pos;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
498 if (size > 1) len -= len % size;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
499 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
500
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
501 if (len <= 0) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
502 return len;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
503 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
504
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
505 memcpy(ptr, buffer->bytes + buffer->pos, len);
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
506 buffer->pos += len;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
507
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
508 return len / size;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
509 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
510
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
511 int cxBufferGet(CxBuffer *buffer) {
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
512 if (cxBufferEof(buffer)) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
513 return EOF;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
514 } else {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
515 int c = buffer->bytes[buffer->pos];
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
516 buffer->pos++;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
517 return c;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
518 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
519 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
520
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
521 int cxBufferShiftLeft(
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
522 CxBuffer *buffer,
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
523 size_t shift
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
524 ) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
525 if (shift >= buffer->size) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
526 buffer->pos = buffer->size = 0;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
527 } else {
1028
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
528 if (buffer_copy_on_write(buffer)) return -1;
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
529 memmove(buffer->bytes, buffer->bytes + shift, buffer->size - shift);
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
530 buffer->size -= shift;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
531
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
532 if (buffer->pos >= shift) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
533 buffer->pos -= shift;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
534 } else {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
535 buffer->pos = 0;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
536 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
537 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
538 return 0;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
539 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
540
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
541 int cxBufferShiftRight(
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
542 CxBuffer *buffer,
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
543 size_t shift
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
544 ) {
1040
1ecf4dbbc60c add some more overflow treatment and make sure to set errno properly
Mike Becker <universe@uap-core.de>
parents: 1030
diff changeset
545 if (buffer->size > SIZE_MAX - shift) {
1ecf4dbbc60c add some more overflow treatment and make sure to set errno properly
Mike Becker <universe@uap-core.de>
parents: 1030
diff changeset
546 errno = EOVERFLOW;
1ecf4dbbc60c add some more overflow treatment and make sure to set errno properly
Mike Becker <universe@uap-core.de>
parents: 1030
diff changeset
547 return -1;
1ecf4dbbc60c add some more overflow treatment and make sure to set errno properly
Mike Becker <universe@uap-core.de>
parents: 1030
diff changeset
548 }
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
549 size_t req_capacity = buffer->size + shift;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
550 size_t movebytes;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
551
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
552 // auto extend buffer, if required and enabled
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
553 if (buffer->capacity < req_capacity) {
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
554 if (buffer->flags & CX_BUFFER_AUTO_EXTEND) {
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
555 if (cxBufferMinimumCapacity(buffer, req_capacity)) {
1065
6eb7b54975ee improve coverage metrics
Mike Becker <universe@uap-core.de>
parents: 1040
diff changeset
556 return -1; // LCOV_EXCL_LINE
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
557 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
558 movebytes = buffer->size;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
559 } else {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
560 movebytes = buffer->capacity - shift;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
561 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
562 } else {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
563 movebytes = buffer->size;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
564 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
565
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
566 if (movebytes > 0) {
1028
3e4905241838 add copy-on-extend feature to UCX buffer - fixes #533
Mike Becker <universe@uap-core.de>
parents: 1024
diff changeset
567 if (buffer_copy_on_write(buffer)) return -1;
1024
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
568 memmove(buffer->bytes + shift, buffer->bytes, movebytes);
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
569 buffer->size = shift + movebytes;
8f99f6c28bd3 add copy-on-write feature to UCX buffer - fixes #531
Mike Becker <universe@uap-core.de>
parents: 1007
diff changeset
570 }
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
571
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
572 buffer->pos += shift;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
573 if (buffer->pos > buffer->size) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
574 buffer->pos = buffer->size;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
575 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
576
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
577 return 0;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
578 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
579
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
580 int cxBufferShift(
500
eb9e7bd40a8e do not hide pointers behind typedefs
Mike Becker <universe@uap-core.de>
parents: 489
diff changeset
581 CxBuffer *buffer,
483
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
582 off_t shift
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
583 ) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
584 if (shift < 0) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
585 return cxBufferShiftLeft(buffer, (size_t) (-shift));
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
586 } else if (shift > 0) {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
587 return cxBufferShiftRight(buffer, (size_t) shift);
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
588 } else {
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
589 return 0;
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
590 }
929016224c3c add ported UCX buffer implementation
Mike Becker <universe@uap-core.de>
parents:
diff changeset
591 }

mercurial