summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorTyge Løvset <[email protected]>2023-06-09 19:31:59 +0200
committerTyge Løvset <[email protected]>2023-06-09 19:31:59 +0200
commit72b0f0e7839b487a5df7c79ffe84511480cad251 (patch)
treee38e997c39bbaad183250c39971222e48bb2d59e
parentabd3b4372dee2291a81271f02588228279139960 (diff)
downloadSTC-modified-72b0f0e7839b487a5df7c79ffe84511480cad251.tar.gz
STC-modified-72b0f0e7839b487a5df7c79ffe84511480cad251.zip
Fixed issues with linking params i_implement, i_extern.
-rw-r--r--docs/cregex_api.md6
-rw-r--r--include/c11/fmt.h1
-rw-r--r--include/stc/cbits.h6
-rw-r--r--include/stc/ccommon.h2
-rw-r--r--include/stc/cdeq.h2
-rw-r--r--include/stc/clist.h2
-rw-r--r--include/stc/cmap.h2
-rw-r--r--include/stc/cpque.h2
-rw-r--r--include/stc/cqueue.h2
-rw-r--r--include/stc/crand.h2
-rw-r--r--include/stc/cregex.h10
-rw-r--r--include/stc/csmap.h2
-rw-r--r--include/stc/cspan.h2
-rw-r--r--include/stc/cstr.h102
-rw-r--r--include/stc/csview.h36
-rw-r--r--include/stc/cvec.h2
-rw-r--r--include/stc/forward.h1
-rw-r--r--include/stc/utf8.h16
-rw-r--r--misc/examples/arc_containers.c2
-rw-r--r--misc/examples/astar.c1
-rw-r--r--misc/examples/books.c1
-rw-r--r--misc/examples/box.c1
-rw-r--r--misc/examples/complex.c3
-rw-r--r--misc/examples/convert.c2
-rw-r--r--misc/examples/coread.c2
-rw-r--r--misc/examples/csmap_erase.c1
-rw-r--r--misc/examples/csmap_find.c1
-rw-r--r--misc/examples/csmap_insert.c1
-rw-r--r--misc/examples/cstr_match.c1
-rw-r--r--misc/examples/demos.c1
-rw-r--r--misc/examples/forfilter.c1
-rw-r--r--misc/examples/gauss2.c3
-rw-r--r--misc/examples/hashmap.c1
-rw-r--r--misc/examples/inits.c2
-rw-r--r--misc/examples/list_splice.c1
-rwxr-xr-xmisc/examples/make.sh2
-rw-r--r--misc/examples/mapmap.c2
-rw-r--r--misc/examples/mmap.c1
-rw-r--r--misc/examples/multimap.c1
-rw-r--r--misc/examples/music_arc.c1
-rw-r--r--misc/examples/new_map.c1
-rw-r--r--misc/examples/new_smap.c1
-rw-r--r--misc/examples/new_sptr.c1
-rw-r--r--misc/examples/person_arc.c1
-rw-r--r--misc/examples/phonebook.c2
-rw-r--r--misc/examples/printspan.c1
-rw-r--r--misc/examples/rawptr_elements.c2
-rw-r--r--misc/examples/read.c1
-rw-r--r--misc/examples/regex_match.c1
-rw-r--r--misc/examples/replace.c1
-rw-r--r--misc/examples/splitstr.c1
-rw-r--r--misc/examples/sso_map.c1
-rw-r--r--misc/examples/sso_substr.c2
-rw-r--r--misc/examples/sview_split.c2
-rw-r--r--misc/examples/unordered_set.c1
-rw-r--r--misc/examples/utf8replace_c.c1
-rw-r--r--misc/examples/vikings.c1
-rw-r--r--src/cregex.c19
-rw-r--r--src/libstc.c12
-rw-r--r--src/utf8code.c5
60 files changed, 180 insertions, 107 deletions
diff --git a/docs/cregex_api.md b/docs/cregex_api.md
index e702c47c..fc86cc63 100644
--- a/docs/cregex_api.md
+++ b/docs/cregex_api.md
@@ -44,15 +44,15 @@ bool cregex_is_match(const cregex* re, const char* input);
// Replace all matches in input
cstr cregex_replace(const cregex* re, const char* input, const char* replace, int count = INT_MAX);
- // Replace count matches in input string-view. Optionally transform replacement with mfun.
+ // Replace count matches in input string-view. Optionally transform replacement.
cstr cregex_replace_sv(const cregex* re, csview input, const char* replace, int count = INT_MAX);
cstr cregex_replace_sv(const cregex* re, csview input, const char* replace, int count,
- bool(*mfun)(int capgrp, csview match, cstr* mstr), int rflags);
+ bool(*transform)(int group, csview match, cstr* result), int rflags);
// All-in-one replacement (compile + find/replace + drop)
cstr cregex_replace_pattern(const char* pattern, const char* input, const char* replace, int count = INT_MAX);
cstr cregex_replace_pattern(const char* pattern, const char* input, const char* replace, int count,
- bool(*mfun)(int capgrp, csview match, cstr* mstr), int rflags);
+ bool(*transform)(int group, csview match, cstr* result), int rflags);
// destroy
void cregex_drop(cregex* self);
```
diff --git a/include/c11/fmt.h b/include/c11/fmt.h
index 7e85e4dd..45044e33 100644
--- a/include/c11/fmt.h
+++ b/include/c11/fmt.h
@@ -69,6 +69,7 @@ int main() {
*/
#include <stdio.h>
#include <stdint.h>
+#include <stddef.h>
#include <assert.h>
#define fmt_OVERLOAD(name, ...) \
diff --git a/include/stc/cbits.h b/include/stc/cbits.h
index fe422202..8a6558bf 100644
--- a/include/stc/cbits.h
+++ b/include/stc/cbits.h
@@ -161,9 +161,9 @@ STC_INLINE void cbits_resize(cbits* self, const int64_t size, const bool value)
if (new_n >= old_n) {
c_memset(self->data64 + old_n, -(int)value, (new_n - old_n)*8);
if (old_n > 0) {
- uint64_t m = _cbits_bit(osize) - 1; /* mask */
- value ? (self->data64[old_n - 1] |= ~m)
- : (self->data64[old_n - 1] &= m);
+ uint64_t mask = _cbits_bit(osize) - 1;
+ if (value) self->data64[old_n - 1] |= ~mask;
+ else self->data64[old_n - 1] &= mask;
}
}
}
diff --git a/include/stc/ccommon.h b/include/stc/ccommon.h
index 01ead57a..87522a6e 100644
--- a/include/stc/ccommon.h
+++ b/include/stc/ccommon.h
@@ -253,6 +253,6 @@ STC_INLINE intptr_t cnextpow2(intptr_t n) {
#if defined(STC_EXTERN)
#define i_extern
#endif
-#if defined(i_static) || defined(STC_IMPLEMENT) || defined(i_extern)
+#if defined(STC_IMPLEMENT) || defined(i_extern)
#define i_implement
#endif
diff --git a/include/stc/cdeq.h b/include/stc/cdeq.h
index b3714bf8..8bb62602 100644
--- a/include/stc/cdeq.h
+++ b/include/stc/cdeq.h
@@ -113,7 +113,7 @@ _cx_memb(_get_mut)(_cx_self* self, _cx_raw raw)
#endif
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
STC_DEF _cx_value*
_cx_memb(_push_front)(_cx_self* self, i_key value) {
diff --git a/include/stc/clist.h b/include/stc/clist.h
index 128e848d..310db204 100644
--- a/include/stc/clist.h
+++ b/include/stc/clist.h
@@ -214,7 +214,7 @@ STC_INLINE bool _cx_memb(_eq)(const _cx_self* self, const _cx_self* other) {
#endif
// -------------------------- IMPLEMENTATION -------------------------
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
#if !defined i_no_clone
STC_DEF _cx_self
diff --git a/include/stc/cmap.h b/include/stc/cmap.h
index 837631f8..f6c3eb07 100644
--- a/include/stc/cmap.h
+++ b/include/stc/cmap.h
@@ -261,7 +261,7 @@ _cx_memb(_eq)(const _cx_self* self, const _cx_self* other) {
}
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
#ifndef i_max_load_factor
#define i_max_load_factor 0.80f
#endif
diff --git a/include/stc/cpque.h b/include/stc/cpque.h
index 85002c67..31a53ece 100644
--- a/include/stc/cpque.h
+++ b/include/stc/cpque.h
@@ -108,7 +108,7 @@ STC_INLINE void _cx_memb(_emplace)(_cx_self* self, _cx_raw raw)
#endif // !i_no_emplace
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
STC_DEF void
_cx_memb(_sift_down_)(_cx_self* self, const intptr_t idx, const intptr_t n) {
diff --git a/include/stc/cqueue.h b/include/stc/cqueue.h
index 571c1fe9..28515877 100644
--- a/include/stc/cqueue.h
+++ b/include/stc/cqueue.h
@@ -121,7 +121,7 @@ STC_INLINE void _cx_memb(_adjust_end_)(_cx_self* self, intptr_t n)
{ self->end = (self->end + n) & self->capmask; }
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
STC_DEF _cx_iter _cx_memb(_advance)(_cx_iter it, intptr_t n) {
intptr_t len = _cx_memb(_size)(it._s);
diff --git a/include/stc/crand.h b/include/stc/crand.h
index f566c1cf..b9687c01 100644
--- a/include/stc/crand.h
+++ b/include/stc/crand.h
@@ -92,7 +92,7 @@ STC_INLINE double crand_f64(crand_t* rng) {
}
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
/* Global random() */
static crand_t crand_global = {{
diff --git a/include/stc/cregex.h b/include/stc/cregex.h
index 919f5474..e6180a31 100644
--- a/include/stc/cregex.h
+++ b/include/stc/cregex.h
@@ -135,7 +135,7 @@ STC_INLINE bool cregex_is_match(const cregex* re, const char* input)
#define cregex_replace_sv_4(pattern, input, replace, count) \
cregex_replace_sv_6(pattern, input, replace, count, NULL, CREG_DEFAULT)
cstr cregex_replace_sv_6(const cregex* re, csview input, const char* replace, int count,
- bool (*mfun)(int i, csview match, cstr* mstr), int rflags);
+ bool (*transform)(int group, csview match, cstr* result), int rflags);
/* replace input with replace using regular expression */
#define cregex_replace(...) c_MACRO_OVERLOAD(cregex_replace, __VA_ARGS__)
@@ -153,20 +153,20 @@ STC_INLINE cstr cregex_replace_4(const cregex* re, const char* input, const char
#define cregex_replace_pattern_4(pattern, input, replace, count) \
cregex_replace_pattern_6(pattern, input, replace, count, NULL, CREG_DEFAULT)
cstr cregex_replace_pattern_6(const char* pattern, const char* input, const char* replace, int count,
- bool (*mfun)(int i, csview match, cstr* mstr), int crflags);
+ bool (*transform)(int group, csview match, cstr* result), int crflags);
/* destroy regex */
void cregex_drop(cregex* re);
-#endif // CREGEX_H_INCLUDED
-#if defined i_extern || defined i_implement
+#if defined i_implement
# include "../../src/cregex.c"
#endif
#if defined i_extern
# include "../../src/utf8code.c"
#endif
+#endif // CREGEX_H_INCLUDED
#undef i_opt
#undef i_header
#undef i_static
-#undef i_implement
#undef i_extern
+#undef i_implement
diff --git a/include/stc/csmap.h b/include/stc/csmap.h
index e8138926..7638b8f2 100644
--- a/include/stc/csmap.h
+++ b/include/stc/csmap.h
@@ -249,7 +249,7 @@ _cx_memb(_from_n)(const _cx_raw* raw, intptr_t n)
{ _cx_self cx = {0}; _cx_memb(_put_n)(&cx, raw, n); return cx; }
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
STC_DEF void
_cx_memb(_next)(_cx_iter *it) {
diff --git a/include/stc/cspan.h b/include/stc/cspan.h
index b07e75a8..5b592098 100644
--- a/include/stc/cspan.h
+++ b/include/stc/cspan.h
@@ -212,7 +212,7 @@ STC_API intptr_t _cspan_slice(int32_t odim[], int32_t ostri[], int* orank,
int rank, const int32_t a[][2]);
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
STC_DEF intptr_t _cspan_idxN(int rank, const int32_t shape[], const int32_t stri[], const int32_t a[]) {
intptr_t off = a[0];
diff --git a/include/stc/cstr.h b/include/stc/cstr.h
index 03eefd2f..ae80dab4 100644
--- a/include/stc/cstr.h
+++ b/include/stc/cstr.h
@@ -24,16 +24,12 @@
/* A string type with short string optimization in C99 with good small-string
* optimization (22 characters with 24 bytes string).
*/
+#define _i_no_undef
+#include "utf8.h"
+
#ifndef CSTR_H_INCLUDED
#define CSTR_H_INCLUDED
-#define i_header
-#if defined i_extern || defined STC_EXTERN
-# define _i_extern
-#endif
-#include "ccommon.h"
-#include "forward.h"
-#include "utf8.h"
#include <stdlib.h> /* malloc */
#include <stdarg.h>
#include <stdio.h> /* vsnprintf */
@@ -65,8 +61,8 @@ enum { cstr_s_cap = sizeof(cstr_buf) - 2 };
#define cstr_l_drop(s) c_free((s)->lon.data)
#define cstr_is_long(s) ((s)->sml.size > 127)
-STC_API char* _cstr_init(cstr* self, intptr_t len, intptr_t cap);
-STC_API char* _cstr_internal_move(cstr* self, intptr_t pos1, intptr_t pos2);
+extern char* _cstr_init(cstr* self, intptr_t len, intptr_t cap);
+extern char* _cstr_internal_move(cstr* self, intptr_t pos1, intptr_t pos2);
/**************************** PUBLIC API **********************************/
@@ -74,19 +70,21 @@ STC_API char* _cstr_internal_move(cstr* self, intptr_t pos1, intptr_t pos2);
#define cstr_NULL (c_LITERAL(cstr){{{0}, 0}})
#define cstr_toraw(self) cstr_str(self)
-STC_API char* cstr_reserve(cstr* self, intptr_t cap);
-STC_API void cstr_shrink_to_fit(cstr* self);
-STC_API char* cstr_resize(cstr* self, intptr_t size, char value);
-STC_API intptr_t cstr_find_at(const cstr* self, intptr_t pos, const char* search);
-STC_API char* cstr_assign_n(cstr* self, const char* str, intptr_t len);
-STC_API char* cstr_append_n(cstr* self, const char* str, intptr_t len);
-STC_API bool cstr_getdelim(cstr *self, int delim, FILE *fp);
-STC_API void cstr_erase(cstr* self, intptr_t pos, intptr_t len);
-STC_API void cstr_u8_erase(cstr* self, intptr_t bytepos, intptr_t u8len);
-STC_API cstr cstr_from_fmt(const char* fmt, ...);
-STC_API intptr_t cstr_append_fmt(cstr* self, const char* fmt, ...);
-STC_API intptr_t cstr_printf(cstr* self, const char* fmt, ...);
-STC_API cstr cstr_replace_sv(csview sv, csview search, csview repl, int32_t count);
+extern char* cstr_reserve(cstr* self, intptr_t cap);
+extern void cstr_shrink_to_fit(cstr* self);
+extern char* cstr_resize(cstr* self, intptr_t size, char value);
+extern intptr_t cstr_find_at(const cstr* self, intptr_t pos, const char* search);
+extern intptr_t cstr_find_sv(const cstr* self, csview search);
+extern char* cstr_assign_n(cstr* self, const char* str, intptr_t len);
+extern char* cstr_append_n(cstr* self, const char* str, intptr_t len);
+extern bool cstr_getdelim(cstr *self, int delim, FILE *fp);
+extern void cstr_erase(cstr* self, intptr_t pos, intptr_t len);
+extern void cstr_u8_erase(cstr* self, intptr_t bytepos, intptr_t u8len);
+extern cstr cstr_from_fmt(const char* fmt, ...);
+extern intptr_t cstr_append_fmt(cstr* self, const char* fmt, ...);
+extern intptr_t cstr_printf(cstr* self, const char* fmt, ...);
+extern cstr cstr_replace_sv(csview sv, csview search, csview repl, int32_t count);
+extern uint64_t cstr_hash(const cstr *self);
STC_INLINE cstr_buf cstr_buffer(cstr* s) {
return cstr_is_long(s)
@@ -284,8 +282,6 @@ STC_INLINE intptr_t cstr_find(const cstr* self, const char* search) {
return res ? (res - str) : c_NPOS;
}
-STC_API intptr_t cstr_find_sv(const cstr* self, csview search);
-
STC_INLINE intptr_t cstr_find_s(const cstr* self, cstr search)
{ return cstr_find(self, cstr_str(&search)); }
@@ -404,13 +400,15 @@ STC_INLINE void cstr_insert_s(cstr* self, intptr_t pos, cstr s) {
cstr_replace_at_sv(self, pos, 0, sv);
}
-
STC_INLINE bool cstr_getline(cstr *self, FILE *fp)
{ return cstr_getdelim(self, '\n', fp); }
-STC_API uint64_t cstr_hash(const cstr *self);
+#endif // CSTR_H_INCLUDED
+
+/* -------------------------- EXTERN ------------------------- */
+#if defined(i_extern) && !defined(CSTR_X_INCLUDED)
+#define CSTR_X_INCLUDED
-#ifdef _i_extern
static struct {
int (*conv_asc)(int);
uint32_t (*conv_utf)(uint32_t);
@@ -439,23 +437,25 @@ cstr cstr_tocase(csview sv, int k) {
cstr_shrink_to_fit(&out);
return out;
}
-#endif
+#endif // i_extern
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#ifndef CSTR_C_INCLUDED
+#if defined i_extern || (defined i_implement && !defined _i_no_undef)
+#define CSTR_C_INCLUDED
-STC_DEF uint64_t cstr_hash(const cstr *self) {
+uint64_t cstr_hash(const cstr *self) {
csview sv = cstr_sv(self);
return cfasthash(sv.str, sv.size);
}
-STC_DEF intptr_t cstr_find_sv(const cstr* self, csview search) {
+intptr_t cstr_find_sv(const cstr* self, csview search) {
csview sv = cstr_sv(self);
char* res = cstrnstrn(sv.str, search.str, sv.size, search.size);
return res ? (res - sv.str) : c_NPOS;
}
-STC_DEF char* _cstr_internal_move(cstr* self, const intptr_t pos1, const intptr_t pos2) {
+char* _cstr_internal_move(cstr* self, const intptr_t pos1, const intptr_t pos2) {
cstr_buf r = cstr_buffer(self);
if (pos1 != pos2) {
const intptr_t newlen = (r.size + pos2 - pos1);
@@ -467,7 +467,7 @@ STC_DEF char* _cstr_internal_move(cstr* self, const intptr_t pos1, const intptr_
return r.data;
}
-STC_DEF char* _cstr_init(cstr* self, const intptr_t len, const intptr_t cap) {
+char* _cstr_init(cstr* self, const intptr_t len, const intptr_t cap) {
if (cap > cstr_s_cap) {
self->lon.data = (char *)c_malloc(cap + 1);
cstr_l_set_size(self, len);
@@ -478,7 +478,7 @@ STC_DEF char* _cstr_init(cstr* self, const intptr_t len, const intptr_t cap) {
return self->sml.data;
}
-STC_DEF void cstr_shrink_to_fit(cstr* self) {
+void cstr_shrink_to_fit(cstr* self) {
cstr_buf r = cstr_buffer(self);
if (r.size == r.cap)
return;
@@ -492,7 +492,7 @@ STC_DEF void cstr_shrink_to_fit(cstr* self) {
}
}
-STC_DEF char* cstr_reserve(cstr* self, const intptr_t cap) {
+char* cstr_reserve(cstr* self, const intptr_t cap) {
if (cstr_is_long(self)) {
if (cap > cstr_l_cap(self)) {
self->lon.data = (char *)c_realloc(self->lon.data, cap + 1);
@@ -505,7 +505,7 @@ STC_DEF char* cstr_reserve(cstr* self, const intptr_t cap) {
char* data = (char *)c_malloc(cap + 1);
const intptr_t len = cstr_s_size(self);
/* copy full short buffer to emulate realloc() */
- c_memcpy(data, self->sml.data, cstr_s_cap + 2);
+ c_memcpy(data, self->sml.data, sizeof self->sml);
self->lon.data = data;
self->lon.size = (size_t)len;
cstr_l_set_cap(self, cap);
@@ -514,7 +514,7 @@ STC_DEF char* cstr_reserve(cstr* self, const intptr_t cap) {
return self->sml.data;
}
-STC_DEF char* cstr_resize(cstr* self, const intptr_t size, const char value) {
+char* cstr_resize(cstr* self, const intptr_t size, const char value) {
cstr_buf r = cstr_buffer(self);
if (size > r.size) {
if (size > r.cap && !(r.data = cstr_reserve(self, size)))
@@ -525,20 +525,20 @@ STC_DEF char* cstr_resize(cstr* self, const intptr_t size, const char value) {
return r.data;
}
-STC_DEF intptr_t cstr_find_at(const cstr* self, const intptr_t pos, const char* search) {
+intptr_t cstr_find_at(const cstr* self, const intptr_t pos, const char* search) {
csview sv = cstr_sv(self);
if (pos > sv.size) return c_NPOS;
const char* res = strstr((char*)sv.str + pos, search);
return res ? (res - sv.str) : c_NPOS;
}
-STC_DEF char* cstr_assign_n(cstr* self, const char* str, const intptr_t len) {
+char* cstr_assign_n(cstr* self, const char* str, const intptr_t len) {
char* d = cstr_reserve(self, len);
if (d) { c_memmove(d, str, len); _cstr_set_size(self, len); }
return d;
}
-STC_DEF char* cstr_append_n(cstr* self, const char* str, const intptr_t len) {
+char* cstr_append_n(cstr* self, const char* str, const intptr_t len) {
cstr_buf r = cstr_buffer(self);
if (r.size + len > r.cap) {
const size_t off = (size_t)(str - r.data);
@@ -551,7 +551,7 @@ STC_DEF char* cstr_append_n(cstr* self, const char* str, const intptr_t len) {
return r.data;
}
-STC_DEF bool cstr_getdelim(cstr *self, const int delim, FILE *fp) {
+bool cstr_getdelim(cstr *self, const int delim, FILE *fp) {
int c = fgetc(fp);
if (c == EOF)
return false;
@@ -571,7 +571,7 @@ STC_DEF bool cstr_getdelim(cstr *self, const int delim, FILE *fp) {
}
}
-STC_DEF cstr
+cstr
cstr_replace_sv(csview in, csview search, csview repl, int32_t count) {
cstr out = cstr_NULL;
intptr_t from = 0; char* res;
@@ -587,14 +587,14 @@ cstr_replace_sv(csview in, csview search, csview repl, int32_t count) {
return out;
}
-STC_DEF void cstr_erase(cstr* self, const intptr_t pos, intptr_t len) {
+void cstr_erase(cstr* self, const intptr_t pos, intptr_t len) {
cstr_buf r = cstr_buffer(self);
if (len > r.size - pos) len = r.size - pos;
c_memmove(&r.data[pos], &r.data[pos + len], r.size - (pos + len));
_cstr_set_size(self, r.size - len);
}
-STC_DEF void cstr_u8_erase(cstr* self, const intptr_t bytepos, const intptr_t u8len) {
+void cstr_u8_erase(cstr* self, const intptr_t bytepos, const intptr_t u8len) {
cstr_buf r = cstr_buffer(self);
intptr_t len = utf8_pos(r.data + bytepos, u8len);
c_memmove(&r.data[bytepos], &r.data[bytepos + len], r.size - (bytepos + len));
@@ -609,7 +609,7 @@ STC_DEF void cstr_u8_erase(cstr* self, const intptr_t bytepos, const intptr_t u8
# pragma warning(disable: 4996)
#endif
-STC_DEF intptr_t cstr_vfmt(cstr* self, intptr_t start, const char* fmt, va_list args) {
+intptr_t cstr_vfmt(cstr* self, intptr_t start, const char* fmt, va_list args) {
va_list args2;
va_copy(args2, args);
const int n = vsnprintf(NULL, 0ULL, fmt, args);
@@ -624,7 +624,7 @@ STC_DEF intptr_t cstr_vfmt(cstr* self, intptr_t start, const char* fmt, va_list
# pragma warning(pop)
#endif
-STC_DEF cstr cstr_from_fmt(const char* fmt, ...) {
+cstr cstr_from_fmt(const char* fmt, ...) {
cstr s = cstr_NULL;
va_list args;
va_start(args, fmt);
@@ -633,7 +633,7 @@ STC_DEF cstr cstr_from_fmt(const char* fmt, ...) {
return s;
}
-STC_DEF intptr_t cstr_append_fmt(cstr* self, const char* fmt, ...) {
+intptr_t cstr_append_fmt(cstr* self, const char* fmt, ...) {
va_list args;
va_start(args, fmt);
const intptr_t n = cstr_vfmt(self, cstr_size(self), fmt, args);
@@ -642,21 +642,21 @@ STC_DEF intptr_t cstr_append_fmt(cstr* self, const char* fmt, ...) {
}
/* NB! self-data in args is UB */
-STC_DEF intptr_t cstr_printf(cstr* self, const char* fmt, ...) {
+intptr_t cstr_printf(cstr* self, const char* fmt, ...) {
va_list args;
va_start(args, fmt);
const intptr_t n = cstr_vfmt(self, 0, fmt, args);
va_end(args);
return n;
}
-
#endif // i_implement
+#endif // CSTR_C_INCLUDED
+
#if defined __GNUC__ && !defined __clang__
# pragma GCC diagnostic pop
#endif
-#endif // CSTR_H_INCLUDED
#undef i_opt
#undef i_header
#undef i_static
#undef i_implement
-#undef _i_extern
+#undef i_extern
diff --git a/include/stc/csview.h b/include/stc/csview.h
index e8a3ad9b..d38d5f59 100644
--- a/include/stc/csview.h
+++ b/include/stc/csview.h
@@ -20,12 +20,12 @@
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
+#define _i_no_undef
+#include "utf8.h"
+
#ifndef CSVIEW_H_INCLUDED
#define CSVIEW_H_INCLUDED
-#include "ccommon.h"
-#include "utf8.h"
-
#define csview_NULL c_sv_1("")
#define csview_init() csview_NULL
#define csview_drop(p) c_default_drop(p)
@@ -33,12 +33,12 @@
#define csview_lit(literal) c_sv_1(literal)
#define csview_from_n(str, n) c_sv_2(str, n)
-STC_API csview_iter csview_advance(csview_iter it, intptr_t pos);
-STC_API intptr_t csview_find_sv(csview sv, csview search);
-STC_API uint64_t csview_hash(const csview *self);
-STC_API csview csview_slice_ex(csview sv, intptr_t p1, intptr_t p2);
-STC_API csview csview_substr_ex(csview sv, intptr_t pos, intptr_t n);
-STC_API csview csview_token(csview sv, const char* sep, intptr_t* start);
+extern csview_iter csview_advance(csview_iter it, intptr_t pos);
+extern intptr_t csview_find_sv(csview sv, csview search);
+extern uint64_t csview_hash(const csview *self);
+extern csview csview_slice_ex(csview sv, intptr_t p1, intptr_t p2);
+extern csview csview_substr_ex(csview sv, intptr_t pos, intptr_t n);
+extern csview csview_token(csview sv, const char* sep, intptr_t* start);
STC_INLINE csview csview_from(const char* str)
{ return c_LITERAL(csview){str, c_strlen(str)}; }
@@ -147,10 +147,14 @@ STC_INLINE int csview_icmp(const csview* x, const csview* y)
STC_INLINE bool csview_eq(const csview* x, const csview* y)
{ return x->size == y->size && !c_memcmp(x->str, y->str, x->size); }
+#endif // CSVIEW_H_INCLUDED
+
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#ifndef CSVIEW_C_INCLUDED
+#if defined i_extern || (defined i_implement && !defined _i_no_undef)
+#define CSVIEW_C_INCLUDED
-STC_DEF csview_iter csview_advance(csview_iter it, intptr_t pos) {
+csview_iter csview_advance(csview_iter it, intptr_t pos) {
int inc = -1;
if (pos > 0) pos = -pos, inc = 1;
while (pos && it.ref != it.u8.end) pos += (*(it.ref += inc) & 0xC0) != 0x80;
@@ -159,15 +163,15 @@ STC_DEF csview_iter csview_advance(csview_iter it, intptr_t pos) {
return it;
}
-STC_DEF intptr_t csview_find_sv(csview sv, csview search) {
+intptr_t csview_find_sv(csview sv, csview search) {
char* res = cstrnstrn(sv.str, search.str, sv.size, search.size);
return res ? (res - sv.str) : c_NPOS;
}
-STC_DEF uint64_t csview_hash(const csview *self)
+uint64_t csview_hash(const csview *self)
{ return cfasthash(self->str, self->size); }
-STC_DEF csview csview_substr_ex(csview sv, intptr_t pos, intptr_t n) {
+csview csview_substr_ex(csview sv, intptr_t pos, intptr_t n) {
if (pos < 0) {
pos += sv.size;
if (pos < 0) pos = 0;
@@ -178,7 +182,7 @@ STC_DEF csview csview_substr_ex(csview sv, intptr_t pos, intptr_t n) {
return sv;
}
-STC_DEF csview csview_slice_ex(csview sv, intptr_t p1, intptr_t p2) {
+csview csview_slice_ex(csview sv, intptr_t p1, intptr_t p2) {
if (p1 < 0) {
p1 += sv.size;
if (p1 < 0) p1 = 0;
@@ -189,7 +193,7 @@ STC_DEF csview csview_slice_ex(csview sv, intptr_t p1, intptr_t p2) {
return sv;
}
-STC_DEF csview csview_token(csview sv, const char* sep, intptr_t* start) {
+csview csview_token(csview sv, const char* sep, intptr_t* start) {
intptr_t sep_size = c_strlen(sep);
csview slice = {sv.str + *start, sv.size - *start};
const char* res = cstrnstrn(slice.str, sep, slice.size, sep_size);
diff --git a/include/stc/cvec.h b/include/stc/cvec.h
index 512dbf67..747c654d 100644
--- a/include/stc/cvec.h
+++ b/include/stc/cvec.h
@@ -264,7 +264,7 @@ _cx_memb(_sort)(_cx_self* self) {
}
#endif // !c_no_cmp
/* -------------------------- IMPLEMENTATION ------------------------- */
-#if defined(i_implement)
+#if defined(i_implement) || defined(i_static)
STC_DEF _cx_self
_cx_memb(_init)(void) {
diff --git a/include/stc/forward.h b/include/stc/forward.h
index 9eafb857..484a8b63 100644
--- a/include/stc/forward.h
+++ b/include/stc/forward.h
@@ -24,6 +24,7 @@
#define STC_FORWARD_H_INCLUDED
#include <stdint.h>
+#include <stddef.h>
#define forward_carc(CX, VAL) _c_carc_types(CX, VAL)
#define forward_cbox(CX, VAL) _c_cbox_types(CX, VAL)
diff --git a/include/stc/utf8.h b/include/stc/utf8.h
index a4cc3846..338f0db9 100644
--- a/include/stc/utf8.h
+++ b/include/stc/utf8.h
@@ -1,3 +1,4 @@
+
#ifndef UTF8_H_INCLUDED
#define UTF8_H_INCLUDED
@@ -5,7 +6,6 @@
#include "forward.h"
#include "ccommon.h"
-// utf8 methods defined in src/utf8code.c:
enum {
U8G_Cc, U8G_Lt, U8G_Nd, U8G_Nl,
U8G_Pc, U8G_Pd, U8G_Pf, U8G_Pi,
@@ -16,6 +16,7 @@ enum {
U8G_SIZE
};
+// utf8 methods defined in src/utf8code.c:
extern bool utf8_isgroup(int group, uint32_t c);
extern bool utf8_isalpha(uint32_t c);
extern uint32_t utf8_casefold(uint32_t c);
@@ -112,9 +113,16 @@ STC_INLINE const char* utf8_at(const char *s, intptr_t index) {
STC_INLINE intptr_t utf8_pos(const char* s, intptr_t index)
{ return (intptr_t)(utf8_at(s, index) - s); }
-
#endif // UTF8_H_INCLUDED
-#if defined(i_extern)
+
+#if defined i_extern || (defined i_implement && !defined _i_no_undef)
# include "../../src/utf8code.c"
-# undef i_extern
#endif
+#ifndef _i_no_undef
+#undef i_static
+#undef i_header
+#undef i_implement
+#undef i_extern
+#undef i_opt
+#endif
+#undef _i_no_undef
diff --git a/misc/examples/arc_containers.c b/misc/examples/arc_containers.c
index d6a0afa8..7038734e 100644
--- a/misc/examples/arc_containers.c
+++ b/misc/examples/arc_containers.c
@@ -1,6 +1,6 @@
// Create a stack and a list of shared pointers to maps,
// and demonstrate sharing and cloning of maps.
-#define i_static
+#define i_implement
#include <stc/cstr.h>
#include <stc/algo/raii.h>
#define i_type Map
diff --git a/misc/examples/astar.c b/misc/examples/astar.c
index dae6d609..db6bbd70 100644
--- a/misc/examples/astar.c
+++ b/misc/examples/astar.c
@@ -4,6 +4,7 @@
// This is a reimplementation of the CTL example to STC:
// https://github.com/glouw/ctl/blob/master/examples/astar.c
// https://www.redblobgames.com/pathfinding/a-star/introduction.html
+#define i_implement
#include <stc/cstr.h>
#include <stc/algo/raii.h>
#include <stdio.h>
diff --git a/misc/examples/books.c b/misc/examples/books.c
index a62769b0..7f0660b8 100644
--- a/misc/examples/books.c
+++ b/misc/examples/books.c
@@ -1,4 +1,5 @@
// https://doc.rust-lang.org/std/collections/struct.HashMap.html
+#define i_implement
#include <stc/cstr.h>
#define i_key_str
#define i_val_str
diff --git a/misc/examples/box.c b/misc/examples/box.c
index 9954883c..e352aa2b 100644
--- a/misc/examples/box.c
+++ b/misc/examples/box.c
@@ -1,4 +1,5 @@
/* cbox: heap allocated boxed type */
+#define i_implement
#include <stc/cstr.h>
typedef struct { cstr name, last; } Person;
diff --git a/misc/examples/complex.c b/misc/examples/complex.c
index c730db33..2d8dbf62 100644
--- a/misc/examples/complex.c
+++ b/misc/examples/complex.c
@@ -5,10 +5,9 @@
// using StackList = std::stack<FloatStack>;
// using ListMap = std::unordered_map<int, std::forward_list<StackList>>;
// using MapMap = std::unordered_map<std::string, ListMap>;
-
+#define i_implement
#include <stc/cstr.h>
-
#define i_type FloatStack
#define i_val float
#include <stc/cstack.h>
diff --git a/misc/examples/convert.c b/misc/examples/convert.c
index c5649c55..318f09b8 100644
--- a/misc/examples/convert.c
+++ b/misc/examples/convert.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
#include <stc/algo/raii.h>
@@ -9,7 +10,6 @@
#include <stc/cvec.h>
#define i_val_str
-#define i_extern // define _clist_mergesort() once
#include <stc/clist.h>
int main()
diff --git a/misc/examples/coread.c b/misc/examples/coread.c
index 2585fb81..63162ba3 100644
--- a/misc/examples/coread.c
+++ b/misc/examples/coread.c
@@ -1,4 +1,4 @@
-#define i_static
+#define i_implement
#include <stc/cstr.h>
#include <stc/algo/coroutine.h>
#include <errno.h>
diff --git a/misc/examples/csmap_erase.c b/misc/examples/csmap_erase.c
index 568dae29..9433d370 100644
--- a/misc/examples/csmap_erase.c
+++ b/misc/examples/csmap_erase.c
@@ -1,5 +1,6 @@
// map_erase.c
// From C++ example: https://docs.microsoft.com/en-us/cpp/standard-library/map-class?view=msvc-160#example-16
+#define i_implement
#include <stc/cstr.h>
#include <stdio.h>
diff --git a/misc/examples/csmap_find.c b/misc/examples/csmap_find.c
index 92dd0031..a8928410 100644
--- a/misc/examples/csmap_find.c
+++ b/misc/examples/csmap_find.c
@@ -1,5 +1,6 @@
// This implements the c++ std::map::find example at:
// https://docs.microsoft.com/en-us/cpp/standard-library/map-class?view=msvc-160#example-17
+#define i_implement
#include <stc/cstr.h>
#define i_key int
diff --git a/misc/examples/csmap_insert.c b/misc/examples/csmap_insert.c
index 7708fdc9..f96cc08f 100644
--- a/misc/examples/csmap_insert.c
+++ b/misc/examples/csmap_insert.c
@@ -5,6 +5,7 @@
#define i_tag ii // Map of int => int
#include <stc/csmap.h>
+#define i_implement
#include <stc/cstr.h>
#define i_key int
#define i_val_str
diff --git a/misc/examples/cstr_match.c b/misc/examples/cstr_match.c
index 58cf8884..10a843cf 100644
--- a/misc/examples/cstr_match.c
+++ b/misc/examples/cstr_match.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
#include <stc/csview.h>
#include <stdio.h>
diff --git a/misc/examples/demos.c b/misc/examples/demos.c
index de92e378..8488dfb9 100644
--- a/misc/examples/demos.c
+++ b/misc/examples/demos.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
void stringdemo1()
diff --git a/misc/examples/forfilter.c b/misc/examples/forfilter.c
index 8ea3e6a1..f9505aa9 100644
--- a/misc/examples/forfilter.c
+++ b/misc/examples/forfilter.c
@@ -1,6 +1,7 @@
#include <stdio.h>
#define i_extern
#include <stc/cstr.h>
+#define i_implement
#include <stc/csview.h>
#include <stc/algo/filter.h>
#include <stc/algo/crange.h>
diff --git a/misc/examples/gauss2.c b/misc/examples/gauss2.c
index e786824b..67586181 100644
--- a/misc/examples/gauss2.c
+++ b/misc/examples/gauss2.c
@@ -1,8 +1,9 @@
#include <stdio.h>
#include <time.h>
-#include <stc/crand.h>
+#define i_implement
#include <stc/cstr.h>
+#include <stc/crand.h>
// Declare int -> int sorted map.
#define i_key int
diff --git a/misc/examples/hashmap.c b/misc/examples/hashmap.c
index 47a3bcff..cf11b7f7 100644
--- a/misc/examples/hashmap.c
+++ b/misc/examples/hashmap.c
@@ -1,4 +1,5 @@
// https://doc.rust-lang.org/rust-by-example/std/hash.html
+#define i_implement
#include <stc/cstr.h>
#define i_key_str
#define i_val_str
diff --git a/misc/examples/inits.c b/misc/examples/inits.c
index 1f01f88a..a3a6c4d2 100644
--- a/misc/examples/inits.c
+++ b/misc/examples/inits.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
#define i_key int
@@ -25,7 +26,6 @@ inline static int ipair_cmp(const ipair_t* a, const ipair_t* b) {
#define i_val ipair_t
#define i_cmp ipair_cmp
#define i_tag ip
-#define i_extern // define _clist_mergesort() once
#include <stc/clist.h>
#define i_val float
diff --git a/misc/examples/list_splice.c b/misc/examples/list_splice.c
index 73015454..e457694d 100644
--- a/misc/examples/list_splice.c
+++ b/misc/examples/list_splice.c
@@ -2,7 +2,6 @@
#define i_val int
#define i_tag i
-#define i_extern // define _clist_mergesort() once
#include <stc/clist.h>
void print_ilist(const char* s, clist_i list)
diff --git a/misc/examples/make.sh b/misc/examples/make.sh
index d58ed0cb..61d9f879 100755
--- a/misc/examples/make.sh
+++ b/misc/examples/make.sh
@@ -6,7 +6,7 @@ if [ "$(uname)" = 'Linux' ]; then
oflag='-o '
fi
-cc=gcc; cflags="-DSTC_STATIC -std=c99 -s -O3 -Wall -Wextra -Wpedantic -Wconversion -Wwrite-strings -Wdouble-promotion -Wno-unused-parameter -Wno-maybe-uninitialized -Wno-implicit-fallthrough -Wno-missing-field-initializers"
+cc=gcc; cflags="-std=c99 -s -O3 -Wall -Wextra -Wpedantic -Wconversion -Wwrite-strings -Wdouble-promotion -Wno-unused-parameter -Wno-maybe-uninitialized -Wno-implicit-fallthrough -Wno-missing-field-initializers"
#cc=gcc; cflags="-DSTC_STATIC -std=c99 -g -Werror -Wfatal-errors -Wpedantic -Wall $sanitize"
#cc=tcc; cflags="-DSTC_STATIC -std=c99 -Wall"
#cc=clang; cflags="-DSTC_STATIC -std=c99 -s -O3 -Wall -Wextra -Wpedantic -Wconversion -Wwrite-strings -Wdouble-promotion -Wno-unused-parameter -Wno-unused-function -Wno-implicit-fallthrough -Wno-missing-field-initializers"
diff --git a/misc/examples/mapmap.c b/misc/examples/mapmap.c
index 668da5de..d3065659 100644
--- a/misc/examples/mapmap.c
+++ b/misc/examples/mapmap.c
@@ -1,5 +1,5 @@
// create a structure like: std::map<std::string, std::map<std::string, std::string>>:
-
+#define i_implement
#include <stc/cstr.h>
// People: std::map<std::string, std::string>
diff --git a/misc/examples/mmap.c b/misc/examples/mmap.c
index 0394a2df..63312e04 100644
--- a/misc/examples/mmap.c
+++ b/misc/examples/mmap.c
@@ -2,6 +2,7 @@
// https://en.cppreference.com/w/cpp/container/multimap/insert
// Multimap entries
+#define i_implement
#include <stc/cstr.h>
#define i_val_str
#include <stc/clist.h>
diff --git a/misc/examples/multimap.c b/misc/examples/multimap.c
index d8981a81..dc4a1ee0 100644
--- a/misc/examples/multimap.c
+++ b/misc/examples/multimap.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
// Olympics multimap example
diff --git a/misc/examples/music_arc.c b/misc/examples/music_arc.c
index 87a57783..9c7173ef 100644
--- a/misc/examples/music_arc.c
+++ b/misc/examples/music_arc.c
@@ -1,5 +1,6 @@
// shared_ptr-examples.cpp
// based on https://docs.microsoft.com/en-us/cpp/cpp/how-to-create-and-use-shared-ptr-instances?view=msvc-160
+#define i_implement
#include <stc/cstr.h>
typedef struct
diff --git a/misc/examples/new_map.c b/misc/examples/new_map.c
index 1f50db83..277bcbc2 100644
--- a/misc/examples/new_map.c
+++ b/misc/examples/new_map.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
#include <stc/forward.h>
diff --git a/misc/examples/new_smap.c b/misc/examples/new_smap.c
index 2eaae836..77c4cdce 100644
--- a/misc/examples/new_smap.c
+++ b/misc/examples/new_smap.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
#include <stc/forward.h>
diff --git a/misc/examples/new_sptr.c b/misc/examples/new_sptr.c
index 1b72e4f5..aa8dd175 100644
--- a/misc/examples/new_sptr.c
+++ b/misc/examples/new_sptr.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
typedef struct { cstr name, last; } Person;
diff --git a/misc/examples/person_arc.c b/misc/examples/person_arc.c
index c931089d..b4b926da 100644
--- a/misc/examples/person_arc.c
+++ b/misc/examples/person_arc.c
@@ -1,4 +1,5 @@
/* cbox: heap allocated boxed type */
+#define i_implement
#include <stc/cstr.h>
#include <stc/algo/raii.h>
diff --git a/misc/examples/phonebook.c b/misc/examples/phonebook.c
index 38a71089..faf7566e 100644
--- a/misc/examples/phonebook.c
+++ b/misc/examples/phonebook.c
@@ -20,7 +20,7 @@
// IN THE SOFTWARE.
// Program to emulates the phone book.
-
+#define i_implement
#include <stc/cstr.h>
#define i_key_str
diff --git a/misc/examples/printspan.c b/misc/examples/printspan.c
index b9ec2476..b5099ed5 100644
--- a/misc/examples/printspan.c
+++ b/misc/examples/printspan.c
@@ -1,6 +1,7 @@
// printspan.c
#include <stdio.h>
+#define i_implement
#include <stc/cstr.h>
#define i_val int
#include <stc/cvec.h>
diff --git a/misc/examples/rawptr_elements.c b/misc/examples/rawptr_elements.c
index 01bcdc44..8dd52aee 100644
--- a/misc/examples/rawptr_elements.c
+++ b/misc/examples/rawptr_elements.c
@@ -1,6 +1,6 @@
#include <stc/ccommon.h>
#include <stdio.h>
-
+#define i_implement
#include <stc/cstr.h>
// Create cmap of cstr => long*
diff --git a/misc/examples/read.c b/misc/examples/read.c
index edc89f0e..545d706a 100644
--- a/misc/examples/read.c
+++ b/misc/examples/read.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
#include <stc/algo/raii.h>
#define i_val_str
diff --git a/misc/examples/regex_match.c b/misc/examples/regex_match.c
index e49ebd0b..b4932015 100644
--- a/misc/examples/regex_match.c
+++ b/misc/examples/regex_match.c
@@ -1,5 +1,6 @@
#define i_extern
#include <stc/cregex.h>
+#define i_implement
#include <stc/csview.h>
#define i_val float
diff --git a/misc/examples/replace.c b/misc/examples/replace.c
index cf5b45cb..9ac26c07 100644
--- a/misc/examples/replace.c
+++ b/misc/examples/replace.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
int main ()
diff --git a/misc/examples/splitstr.c b/misc/examples/splitstr.c
index 2bc6fc07..658c46a1 100644
--- a/misc/examples/splitstr.c
+++ b/misc/examples/splitstr.c
@@ -1,6 +1,7 @@
#include <stdio.h>
#define i_extern // cstr + utf8 functions
#include <stc/cregex.h>
+#define i_implement
#include <stc/csview.h>
int main()
diff --git a/misc/examples/sso_map.c b/misc/examples/sso_map.c
index 70450e21..b78dcb2e 100644
--- a/misc/examples/sso_map.c
+++ b/misc/examples/sso_map.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
#define i_key_str
#define i_val_str
diff --git a/misc/examples/sso_substr.c b/misc/examples/sso_substr.c
index 4b2dbcc8..9b062eed 100644
--- a/misc/examples/sso_substr.c
+++ b/misc/examples/sso_substr.c
@@ -1,4 +1,6 @@
+#define i_implement
#include <stc/cstr.h>
+#define i_implement
#include <stc/csview.h>
int main ()
diff --git a/misc/examples/sview_split.c b/misc/examples/sview_split.c
index 31a28e51..782e4096 100644
--- a/misc/examples/sview_split.c
+++ b/misc/examples/sview_split.c
@@ -1,4 +1,6 @@
+#define i_implement
#include <stc/cstr.h>
+#define i_implement
#include <stc/csview.h>
int main()
diff --git a/misc/examples/unordered_set.c b/misc/examples/unordered_set.c
index 90c78521..006a1e80 100644
--- a/misc/examples/unordered_set.c
+++ b/misc/examples/unordered_set.c
@@ -1,5 +1,6 @@
// https://iq.opengenus.org/containers-cpp-stl/
// C program to demonstrate various function of stc cset
+#define i_implement
#include <stc/cstr.h>
#include <stc/algo/raii.h>
#define i_key_str
diff --git a/misc/examples/utf8replace_c.c b/misc/examples/utf8replace_c.c
index 3cde8701..17352fee 100644
--- a/misc/examples/utf8replace_c.c
+++ b/misc/examples/utf8replace_c.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
int main()
diff --git a/misc/examples/vikings.c b/misc/examples/vikings.c
index abb909c3..cf087119 100644
--- a/misc/examples/vikings.c
+++ b/misc/examples/vikings.c
@@ -1,3 +1,4 @@
+#define i_implement
#include <stc/cstr.h>
typedef struct Viking {
diff --git a/src/cregex.c b/src/cregex.c
index 730d35a4..62a64b11 100644
--- a/src/cregex.c
+++ b/src/cregex.c
@@ -25,9 +25,24 @@ THE SOFTWARE.
*/
#ifndef CREGEX_C_INCLUDED
#define CREGEX_C_INCLUDED
-#include <stc/cstr.h>
-#include <stc/cregex.h> // header only
+
#include <setjmp.h>
+#ifdef i_extern
+# define _i_extern
+#endif
+#ifndef CREGEX_H_INCLUDED
+# include "../include/stc/cregex.h"
+#endif
+#ifdef _i_extern
+# include "utf8code.c"
+#endif
+#ifdef _i_extern
+# define i_implement
+#else
+# undef i_implement
+#endif
+#undef _i_extern
+#include "../include/stc/cstr.h"
typedef uint32_t _Rune; /* Utf8 code point */
typedef int32_t _Token;
diff --git a/src/libstc.c b/src/libstc.c
index bc61e37c..99611e05 100644
--- a/src/libstc.c
+++ b/src/libstc.c
@@ -1,4 +1,16 @@
+#include <stddef.h>
+#if 1
+#define i_extern
+#include "../include/stc/utf8.h"
+#define i_implement
+#include "../include/stc/cstr.h"
+#define i_implement
+#include "../include/stc/cregex.h"
+#define i_implement
+#include "../include/stc/csview.h"
+#else
#define i_extern
#include "../include/stc/cregex.h"
#define i_implement
#include "../include/stc/csview.h"
+#endif
diff --git a/src/utf8code.c b/src/utf8code.c
index 496f5eef..6a133050 100644
--- a/src/utf8code.c
+++ b/src/utf8code.c
@@ -1,6 +1,9 @@
#ifndef UTF8_C_INCLUDED
#define UTF8_C_INCLUDED
-#include <stc/utf8.h> // header only
+
+#ifndef UTF8_H_INCLUDED
+#include "../include/stc/utf8.h" /* header only */
+#endif
#include "utf8tabs.inc"
const uint8_t utf8_dtab[] = {