theBrain 10.0
Loading...
Searching...
No Matches
abrain.c File Reference

tag: nhi1-release-250425 More...

#include <stdlib.h>
#include <stdbool.h>
#include <stdint.h>
#include <string.h>
#include <ctype.h>
#include "sqlite3.h"
#include "msgque_mq.h"
#include "debug_mq.h"
+ Include dependency graph for abrain.c:

Go to the source code of this file.

Data Structures

struct  BrainCtxS
 the local context of the server tool More...
 

Macros

#define META_FILE_NAME   "abrain.c"
 
#define BrainT   ((typeof(MqContextST)) BrainTT)
 
#define BRAINCTX   ((struct BrainCtxS*const)mqctx)
 
#define MQCTX   ((MQ_CTX*const)brain)
 
#define META_CONTEXT_S   mqctx
 
#define SETUP_brain   struct BrainCtxS*const brain = BRAINCTX
 
#define SETUP_db   sqlite3*const db = brain->db
 
#define SETUP_W(sh)
 
#define SETUP_C(sh)
 
#define DbErrorCheck(f)
 
#define CHECK_ARGS(s)
 
#define check_sqlite(E)
 
#define check_NULL(E)
 
#define DB_PREPARE_MAX   100
 
#define READ_C(n)
 
#define IdxGet(...)
 
#define IdxFinalize(...)
 
#define HdlGet(...)
 
#define ctxCleanup(...)
 
#define case1(t, f, c)
 
#define GetFromDBnat(...)
 
#define GetFromDBary(...)
 

Functions

static void BrainHelp (const char *base)
 display help using -h or --help command-line option
 
static enum MkErrorE IdxGet_RT (MK_RT mkrt, MQ_CTX const mqctx, MK_I32 *pidx)
 
static enum MkErrorE IdxFinalize_RT (MK_RT mkrt, MQ_CTX const mqctx, MK_I32 idx)
 
static enum MkErrorE HdlGet_RT (MK_RT mkrt, MQ_CTX const mqctx, sqlite3_stmt **phdl, MK_STRN *pInType, MK_STRN *pInEnd, MK_STRN *pOutType, MK_STRN *pOutEnd)
 
static enum MkErrorE ctxCleanup_RT (MK_RT mkrt, MQ_CTX const mqctx)
 
static enum MkTypeE GetTypeE (MK_STRB t)
 
static MK_STRB GetTypeS (enum MkTypeE const ntype)
 
static enum MkTypeE GetTypeD (sqlite3_stmt *hdl, MK_I32 idx)
 
static enum MkErrorE GetFromDBnat_RT (MK_RT mkrt, MQ_CTX const mqctx, enum MkTypeE ntype, sqlite3_stmt *hdl, MK_I32 idx)
 
static enum MkErrorE GetFromDBary_RT (MK_RT mkrt, MQ_CTX const mqctx, enum MkTypeE ntype, sqlite3_stmt *hdl, MK_I32 idx)
 
static enum MkErrorE STEP (MQ_SERVICE_CALL_ARGS)
 
static enum MkErrorE EXEC (MQ_SERVICE_CALL_ARGS)
 
static enum MkErrorE PREP (MQ_SERVICE_CALL_ARGS)
 
static enum MkErrorE FINA (MQ_SERVICE_CALL_ARGS)
 
static enum MkErrorE OPEN (MQ_SERVICE_CALL_ARGS)
 
static enum MkErrorE CLOS (MQ_SERVICE_CALL_ARGS)
 
static enum MkErrorE BrainCleanup (MQ_SERVICE_CALL_ARGS)
 
static enum MkErrorE BrainSetup (MQ_SERVICE_CALL_ARGS)
 
static enum MkErrorE BrainFactory (MQ_CALLBACK_FACTORY_CTOR_ARGS)
 
int main (const int argc, MK_STRN argv[])
 main entry-point for the tool
 

Variables

static MK_TYP BrainTT = NULL
 link to the MqErrorS object
 

Detailed Description

tag: nhi1-release-250425

Definition in file abrain.c.

Macro Definition Documentation

◆ BRAINCTX

#define BRAINCTX   ((struct BrainCtxS*const)mqctx)

Definition at line 29 of file abrain.c.

◆ BrainT

#define BrainT   ((typeof(MqContextST)) BrainTT)

Definition at line 28 of file abrain.c.

◆ case1

#define case1 ( t,
f,
c )
Value:
case t##T: { \
t dat; \
MkErrorCheck(MkBufferGet ## c(buf,&dat)); \
DbErrorCheck(f(hdl,idx,dat)); \
break; \
}

Definition at line 243 of file abrain.c.

243#define case1(t,f,c) \
244 case t##T: { \
245 t dat; \
246 MkErrorCheck(MkBufferGet ## c(buf,&dat)); \
247 DbErrorCheck(f(hdl,idx,dat)); \
248 break; \
249 }

◆ CHECK_ARGS

#define CHECK_ARGS ( s)
Value:
if (MqReadGetNumItems(mqctx)) { \
return MkErrorSetV_4M (mqctx, __func__, SQLITE_ERROR, "usage: %s (%s)\n", __func__, s); \
}
#define MkErrorSetV_4M(m,...)
MK_NUM MqReadGetNumItems(MQ_CTX const ctx)

Definition at line 47 of file abrain.c.

47#define CHECK_ARGS(s) \
48 if (MqReadGetNumItems(mqctx)) { \
49 return MkErrorSetV_4M (mqctx, __func__, SQLITE_ERROR, "usage: %s (%s)\n", __func__, s); \
50 }

◆ check_NULL

#define check_NULL ( E)
Value:
if (unlikely((E) == NULL))
#define unlikely(x)

Definition at line 53 of file abrain.c.

53#define check_NULL(E) \
54 if (unlikely((E) == NULL))

◆ check_sqlite

#define check_sqlite ( E)
Value:
if (unlikely((E) != SQLITE_OK))

Definition at line 51 of file abrain.c.

51#define check_sqlite(E) \
52 if (unlikely((E) != SQLITE_OK))

◆ ctxCleanup

#define ctxCleanup ( ...)
Value:
static enum MkErrorE ctxCleanup_RT(MK_RT mkrt, MQ_CTX const mqctx)
Definition abrain.c:166
#define MK_RT_CALL

Definition at line 183 of file abrain.c.

◆ DB_PREPARE_MAX

#define DB_PREPARE_MAX   100

Definition at line 56 of file abrain.c.

◆ DbErrorCheck

#define DbErrorCheck ( f)
Value:
if (unlikely((f) != SQLITE_OK)) { \
MkErrorSetC_4M (mqctx, sqlite3_errmsg(brain->db), __func__, sqlite3_extended_errcode(brain->db)); \
goto error; \
}

Definition at line 42 of file abrain.c.

42#define DbErrorCheck(f) \
43 if (unlikely((f) != SQLITE_OK)) { \
44 MkErrorSetC_4M (mqctx, sqlite3_errmsg(brain->db), __func__, sqlite3_extended_errcode(brain->db)); \
45 goto error; \
46 }

◆ GetFromDBary

#define GetFromDBary ( ...)
Value:
static enum MkErrorE GetFromDBary_RT(MK_RT mkrt, MQ_CTX const mqctx, enum MkTypeE ntype, sqlite3_stmt *hdl, MK_I32 idx)
Definition abrain.c:276

Definition at line 300 of file abrain.c.

◆ GetFromDBnat

#define GetFromDBnat ( ...)
Value:
static enum MkErrorE GetFromDBnat_RT(MK_RT mkrt, MQ_CTX const mqctx, enum MkTypeE ntype, sqlite3_stmt *hdl, MK_I32 idx)
Definition abrain.c:251

Definition at line 274 of file abrain.c.

◆ HdlGet

#define HdlGet ( ...)
Value:
HdlGet_RT(MK_RT_CALL __VA_ARGS__)
static enum MkErrorE HdlGet_RT(MK_RT mkrt, MQ_CTX const mqctx, sqlite3_stmt **phdl, MK_STRN *pInType, MK_STRN *pInEnd, MK_STRN *pOutType, MK_STRN *pOutEnd)
Definition abrain.c:139

Definition at line 164 of file abrain.c.

◆ IdxFinalize

#define IdxFinalize ( ...)
Value:
static enum MkErrorE IdxFinalize_RT(MK_RT mkrt, MQ_CTX const mqctx, MK_I32 idx)
Definition abrain.c:122

Definition at line 137 of file abrain.c.

◆ IdxGet

#define IdxGet ( ...)
Value:
IdxGet_RT(MK_RT_CALL __VA_ARGS__)
static enum MkErrorE IdxGet_RT(MK_RT mkrt, MQ_CTX const mqctx, MK_I32 *pidx)
Definition abrain.c:109

Definition at line 120 of file abrain.c.

◆ META_CONTEXT_S

#define META_CONTEXT_S   mqctx

Definition at line 31 of file abrain.c.

◆ META_FILE_NAME

#define META_FILE_NAME   "abrain.c"

Definition at line 12 of file abrain.c.

◆ MQCTX

#define MQCTX   ((MQ_CTX*const)brain)

Definition at line 30 of file abrain.c.

◆ READ_C

#define READ_C ( n)
Value:
MK_STRN n; MkErrorCheck(MqReadSTR(mqctx,&n))
const MK_STRB * MK_STRN
#define MqReadSTR(...)

Definition at line 101 of file abrain.c.

◆ SETUP_brain

#define SETUP_brain   struct BrainCtxS*const brain = BRAINCTX

Definition at line 32 of file abrain.c.

◆ SETUP_C

#define SETUP_C ( sh)
Value:
MK_STRN key; MK_SIZE klen; \
register sqlite3_stmt *hdl= brain->sh
#define SETUP_brain
Definition abrain.c:32
long MK_SIZE

Definition at line 38 of file abrain.c.

38#define SETUP_C(sh) \
39 SETUP_brain; \
40 MK_STRN key; MK_SIZE klen; \
41 register sqlite3_stmt *hdl= brain->sh

◆ SETUP_db

#define SETUP_db   sqlite3*const db = brain->db

Definition at line 33 of file abrain.c.

◆ SETUP_W

#define SETUP_W ( sh)
Value:
MK_I64 key; \
register sqlite3_stmt *hdl= brain->sh
signed long long MK_I64

Definition at line 34 of file abrain.c.

34#define SETUP_W(sh) \
35 SETUP_brain; \
36 MK_I64 key; \
37 register sqlite3_stmt *hdl= brain->sh

Function Documentation

◆ BrainCleanup()

static enum MkErrorE BrainCleanup ( MQ_SERVICE_CALL_ARGS )
static

Definition at line 565 of file abrain.c.

566{
568 MkBufferDelete(brain->buf);
569 MkErrorCheck(ctxCleanup(mqctx));
570
571 return MK_OK;
572error:
573 return MkErrorStack_1X(mqctx);
574}
#define ctxCleanup(...)
Definition abrain.c:183
#define MkBufferDelete(x)
#define MkErrorStack_1X(...)
MK_OK
+ Here is the caller graph for this function:

◆ BrainFactory()

static enum MkErrorE BrainFactory ( MQ_CALLBACK_FACTORY_CTOR_ARGS )
static

Definition at line 596 of file abrain.c.

597{
598 MQ_CTX const mqctx = *contextP = MqContextCreate(BrainTT,tmpl);
599
600 mqctx->setup.isServer = true;
603
604 return MK_OK;
605}
static enum MkErrorE BrainCleanup(MQ_SERVICE_CALL_ARGS)
Definition abrain.c:565
static MK_TYP BrainTT
link to the MqErrorS object
Definition abrain.c:27
static enum MkErrorE BrainSetup(MQ_SERVICE_CALL_ARGS)
Definition abrain.c:577
#define MqContextCreate(...)
MqTokenF fCall
struct MqSetupS setup
struct MqCallbackS ServerCleanup
struct MqCallbackS ServerSetup
bool isServer
+ Here is the caller graph for this function:

◆ BrainHelp()

static void BrainHelp ( const char * base)
static

display help using -h or --help command-line option

Parameters
basethe executable usually: basename(argv[0])

Definition at line 81 of file abrain.c.

82{
83 fprintf (stderr, "usage: %s [OPTION]... [ARGUMENT]...\n", base);
84 fputs ("\n", stderr);
85 fputs (" This tool is the database server of NHI1.\n", stderr);
86 fputs (" main: https://theBrain.nhi1.de\n", stderr);
87 fputs (" tool: https://thebrain.nhi1.de/theBrain.htm\n", stderr);
88 fputs ("\n", stderr);
89 fprintf (stderr, " %s [ARGUMENT]... syntax:\n", base);
90 fprintf (stderr, " aclient [OPTION]... %c %s [OPTION]... [ARGUMENT]\n", MK_ALFA, base);
91 fputs ("\n", stderr);
92 fputs (MqHelp (NULL), stderr);
93 fputs ("\n", stderr);
94 fprintf (stderr," %s [OPTION]:\n", base);
95 fputs (" -h, --help print this help\n", stderr);
96 fputs ("\n", stderr);
97
98 exit(EXIT_SUCCESS);
99}
#define MK_ALFA
MK_STR MqHelp(MK_STRN tool)
+ Here is the caller graph for this function:

◆ BrainSetup()

static enum MkErrorE BrainSetup ( MQ_SERVICE_CALL_ARGS )
static

Definition at line 577 of file abrain.c.

578{
580 brain->prepare_start=0;
581 brain->buf = MkBufferCreate(MkBuffer1024STT,10);
582 MkErrorCheck (MqServiceCreate (mqctx, "OPEN", OPEN, NULL, NULL, NULL));
583
584 return MK_OK;
585error:
586 return MkErrorStack_1X(mqctx);
587}
static enum MkErrorE OPEN(MQ_SERVICE_CALL_ARGS)
Definition abrain.c:526
#define MkBuffer1024STT
#define MkBufferCreate(...)
#define MqServiceCreate(...)
+ Here is the caller graph for this function:

◆ CLOS()

static enum MkErrorE CLOS ( MQ_SERVICE_CALL_ARGS )
static

Definition at line 517 of file abrain.c.

517 {
518 MkErrorCheck (ctxCleanup(mqctx));
519 MkErrorCheck (MqServiceDelete (mqctx, "-ALL"));
520 MkErrorCheck (MqServiceCreate (mqctx, "OPEN", OPEN, NULL, NULL, NULL));
521
522error:
523 return MqSendRETURN(mqctx);
524}
#define MqSendRETURN(...)
#define MqServiceDelete(...)
+ Here is the caller graph for this function:

◆ ctxCleanup_RT()

static enum MkErrorE ctxCleanup_RT ( MK_RT mkrt,
MQ_CTX const mqctx )
static

Definition at line 166 of file abrain.c.

166 {
168 MkSysFree (brain->storage);
169 if (brain->db != NULL) {
170 for (MK_I32 idx=0; idx<brain->prepare_start; idx++) {
171 MkErrorCheck (IdxFinalize (mqctx, idx));
172 }
173 brain->prepare_start=0;
174 DbErrorCheck(sqlite3_close(brain->db))
175 brain->db=NULL;
176 }
177 return MK_OK;
178error:
179 brain->db = NULL;
180 return MkErrorStack_1X(mqctx);
181}
#define DbErrorCheck(f)
Definition abrain.c:42
#define IdxFinalize(...)
Definition abrain.c:137
signed int MK_I32
#define MkSysFree(pointer)

◆ EXEC()

static enum MkErrorE EXEC ( MQ_SERVICE_CALL_ARGS )
static

Definition at line 415 of file abrain.c.

415 {
417 MK_STRN sql;
418 MkErrorCheck(MqReadSTR(mqctx,&sql));
419 DbErrorCheck(sqlite3_exec(brain->db,sql, NULL, NULL, NULL));
420
421error:
422 return MqSendRETURN(mqctx);
423}
+ Here is the caller graph for this function:

◆ FINA()

static enum MkErrorE FINA ( MQ_SERVICE_CALL_ARGS )
static

Definition at line 507 of file abrain.c.

507 {
508 MK_I32 idx;
509 MkErrorCheck(IdxGet(mqctx, &idx));
510 MkErrorCheck(IdxFinalize(mqctx, idx));
511error:
512 return MqSendRETURN(mqctx);
513}
#define IdxGet(...)
Definition abrain.c:120
+ Here is the caller graph for this function:

◆ GetFromDBary_RT()

static enum MkErrorE GetFromDBary_RT ( MK_RT mkrt,
MQ_CTX const mqctx,
enum MkTypeE ntype,
sqlite3_stmt * hdl,
MK_I32 idx )
inlinestatic

Definition at line 276 of file abrain.c.

282 {
283 switch (ntype) {
284 case MK_BINT:
285 MqSendBIN_E(mqctx,MkBinaryCreate(sqlite3_column_bytes(hdl,idx),sqlite3_column_blob(hdl,idx)));
286 break;
287 case MK_STRT:
288 MqSendSTR_E(mqctx,(MK_STRN)sqlite3_column_text(hdl,idx));
289 break;
290 default:
291 MkBufferCastTo_E( MkBufferSetSTR(BRAINCTX->buf, (MK_STRN)sqlite3_column_text(hdl, idx)), ntype);
292 MqSendBUF_E(mqctx, BRAINCTX->buf);
293 break;
294 }
295 return MK_OK;
296error:
297 return MkErrorStack_1X(mqctx);
298}
#define BRAINCTX
Definition abrain.c:29
#define MkBufferCastTo_E(...)
#define MkBufferSetSTR(...)
static MkBinaryR MkBinaryCreate(MK_SIZE size, MK_BINN data)
MK_BINT
MK_STRT
#define MqSendBUF_E(...)
#define MqSendSTR_E(...)
#define MqSendBIN_E(...)

◆ GetFromDBnat_RT()

static enum MkErrorE GetFromDBnat_RT ( MK_RT mkrt,
MQ_CTX const mqctx,
enum MkTypeE ntype,
sqlite3_stmt * hdl,
MK_I32 idx )
inlinestatic

Definition at line 251 of file abrain.c.

257 {
258 switch (ntype) {
259 case MK_STRT: return MqSendSTR(mqctx,(MK_STRN)sqlite3_column_text(hdl,idx));
260 case MK_I32T: return MqSendI32(mqctx,(MK_I32)sqlite3_column_int(hdl,idx));
261 case MK_I16T: return MqSendI16(mqctx,(MK_I16)sqlite3_column_int(hdl,idx));
262 case MK_I8T: return MqSendI8(mqctx,(MK_I8)sqlite3_column_int(hdl,idx));
263 case MK_BOLT: return MqSendBOL(mqctx,(MK_BOL)sqlite3_column_int(hdl,idx));
264 case MK_I64T: return MqSendI64(mqctx,(MK_I64)sqlite3_column_int64(hdl,idx));
265 case MK_DBLT: return MqSendDBL(mqctx,(MK_DBL)sqlite3_column_double(hdl,idx));
266 case MK_FLTT: return MqSendFLT(mqctx,(MK_FLT)sqlite3_column_double(hdl,idx));
267 case MK_BINT: return MqSendBIN(mqctx,MkBinaryCreate(sqlite3_column_bytes(hdl,idx),sqlite3_column_blob(hdl,idx)));
268 case MK_LSTT:
269 return MkErrorSetV_4M (mqctx, __func__, SQLITE_ERROR, "invalid protocoll item '%c'", GetTypeS(ntype));
270 }
271 return MK_BINT;
272}
static MK_STRB GetTypeS(enum MkTypeE const ntype)
Definition abrain.c:207
MK_I8T
MK_I64T
MK_FLTT
MK_I16T
MK_BOLT
MK_DBLT
MK_I32T
MK_LSTT
float MK_FLT
signed char MK_I8
unsigned char MK_BOL
signed short int MK_I16
double MK_DBL
#define MqSendBIN(...)
#define MqSendI8(...)
#define MqSendBOL(...)
#define MqSendI64(...)
#define MqSendI32(...)
#define MqSendI16(...)
#define MqSendSTR(...)
#define MqSendFLT(...)
#define MqSendDBL(...)

◆ GetTypeD()

static enum MkTypeE GetTypeD ( sqlite3_stmt * hdl,
MK_I32 idx )
inlinestatic

Definition at line 223 of file abrain.c.

223 {
224 switch (sqlite3_column_type(hdl,idx)) {
225 case SQLITE_INTEGER:
226 switch (sqlite3_column_bytes(hdl,idx)) {
227 case 1: return MK_I8T;
228 case 2: return MK_I16T;
229 case 3:
230 case 4: return MK_I32T;
231 case 6:
232 case 8: return MK_I64T;
233 }
234 break;
235 case SQLITE_FLOAT: return MK_DBLT;
236 case SQLITE_BLOB: return MK_BINT;
237 case SQLITE_TEXT: return MK_STRT;
238 case SQLITE_NULL: return MK_BINT;
239 }
240 return MK_BINT;
241}
+ Here is the caller graph for this function:

◆ GetTypeE()

static enum MkTypeE GetTypeE ( MK_STRB t)
inlinestatic

Definition at line 191 of file abrain.c.

191 {
192 switch (t) {
193 case 'C': return MK_STRT;
194 case 'I': return MK_I32T;
195 case 'D': return MK_DBLT;
196 case 'W': return MK_I64T;
197 case 'B': return MK_BINT;
198 case 'Y': return MK_I8T;
199 case 'O': return MK_BOLT;
200 case 'S': return MK_I16T;
201 case 'F': return MK_FLTT;
202 case 'L': return MK_LSTT;
203 }
204 return MK_STRT;
205}
+ Here is the caller graph for this function:

◆ GetTypeS()

static MK_STRB GetTypeS ( enum MkTypeE const ntype)
inlinestatic

Definition at line 207 of file abrain.c.

207 {
208 switch (ntype) {
209 case MK_STRT: return 'C';
210 case MK_I32T: return 'I';
211 case MK_DBLT: return 'D';
212 case MK_I64T: return 'W';
213 case MK_BINT: return 'B';
214 case MK_I8T: return 'Y';
215 case MK_BOLT: return 'O';
216 case MK_I16T: return 'S';
217 case MK_FLTT: return 'F';
218 case MK_LSTT: return 'L';
219 }
220 return '*';
221}
+ Here is the caller graph for this function:

◆ HdlGet_RT()

static enum MkErrorE HdlGet_RT ( MK_RT mkrt,
MQ_CTX const mqctx,
sqlite3_stmt ** phdl,
MK_STRN * pInType,
MK_STRN * pInEnd,
MK_STRN * pOutType,
MK_STRN * pOutEnd )
inlinestatic

Definition at line 139 of file abrain.c.

147 {
149 MK_I32 idx;
150 MkErrorCheck (IdxGet (mqctx, &idx));
151 check_NULL(*phdl = brain->prepStmt[idx]) {
152 MkErrorSetV_4M (mqctx, __func__, SQLITE_ERROR, "the prepare-index '%i' was NOT defined", idx);
153 goto error;
154 }
155 *pInType = brain->inType[idx];
156 *pInEnd = brain->inEnd[idx];
157 *pOutType = brain->outType[idx];
158 *pOutEnd = brain->outEnd[idx];
159 return MK_OK;
160error:
161 return MkErrorStack_1X(mqctx);
162}
#define check_NULL(E)
Definition abrain.c:53

◆ IdxFinalize_RT()

static enum MkErrorE IdxFinalize_RT ( MK_RT mkrt,
MQ_CTX const mqctx,
MK_I32 idx )
inlinestatic

Definition at line 122 of file abrain.c.

122 {
124 if (brain->prepStmt[idx] != NULL) {
125 DbErrorCheck(sqlite3_finalize(brain->prepStmt[idx]));
126 brain->prepStmt[idx] = NULL;
127 MkSysFree(brain->inType[idx]);
128 brain->inEnd[idx] = NULL;
129 MkSysFree(brain->outType[idx]);
130 brain->outEnd[idx] = NULL;
131 }
132 return MK_OK;
133error:
134 return MkErrorStack_1X(mqctx);
135}

◆ IdxGet_RT()

static enum MkErrorE IdxGet_RT ( MK_RT mkrt,
MQ_CTX const mqctx,
MK_I32 * pidx )
static

Definition at line 109 of file abrain.c.

109 {
110 MkErrorCheck (MqReadI32 (mqctx, pidx));
111 if (*pidx < 0 || *pidx > DB_PREPARE_MAX-1) {
112 MkErrorSetV_4M (mqctx, __func__, SQLITE_ERROR, "prepare index out of range: 0 <= idx <= %i", DB_PREPARE_MAX-1);
113 goto error;
114 }
115 return MK_OK;
116error:
117 return MkErrorStack_1X(mqctx);
118}
#define DB_PREPARE_MAX
Definition abrain.c:56
#define MqReadI32(...)

◆ main()

int main ( const int argc,
MK_STRN argv[] )

main entry-point for the tool

Parameters
argcthe number of command-line arguments
argvthe command-line arguments as an array of strings
Returns
the exit number

Definition at line 613 of file abrain.c.

617{
618 MqSetup();
620
621 // define the new type
622 BrainTT = MkTypeDup2(MqContextSTT, "BrainTT");
623 BrainTT->objsize = sizeof(struct BrainCtxS);
624 BrainT->fHelp = BrainHelp;
625
626 // parse the command-line
627 MK_BFL args = MkBufferListCreateVC (argc, argv);
628 MQ_CTX mqctx = NULL;
629
630 // call Factory
631 MQ_FCT fct = MqFactoryAdd_2(BrainFactory, "abrain");
632 MqFactoryNew_E (fct, NULL, &mqctx);
633
634 // create the ServerCtxS
635 MqLinkCreate_E (mqctx, args);
636
637 // start event-loop and wait forever
639
640 // finish and exit
641error:
642 MkBufferListDelete(args);
643 MqExit_1 (mqctx);
644}
static enum MkErrorE BrainFactory(MQ_CALLBACK_FACTORY_CTOR_ARGS)
Definition abrain.c:596
static void BrainHelp(const char *base)
display help using -h or --help command-line option
Definition abrain.c:81
#define BrainT
Definition abrain.c:28
#define MkBufferListCreateVC(...)
#define MkBufferListDelete(x)
MK_TIMEOUT_DEFAULT
#define AllRtSetup_NULL
#define MkTypeDup2(...)
#define MqContextSTT
#define MqExit_1(ctx)
#define MqProcessEvent_E(...)
#define MqFactoryNew_E(...)
#define MqFactoryAdd_2(fct, ident)
MQ_WAIT_FOREVER
void MqSetup(void)
the local context of the server tool
Definition abrain.c:59
MQ_CTXR mqctx
the LibMqMsgque context object
Definition abrain.c:60
size_t objsize

◆ OPEN()

static enum MkErrorE OPEN ( MQ_SERVICE_CALL_ARGS )
static

Definition at line 526 of file abrain.c.

526 {
528
529 // open storage
530 {
531 MK_STRN dbstorage;
532 MkErrorCheck(MqReadSTR(mqctx,&dbstorage));
533
534 if (dbstorage == NULL) {
535 return MkErrorSetC_4M (mqctx, "storage-file is empty or invalid", __func__, SQLITE_ERROR);
536 }
537
538 MkDLogV(mqctx,5,"try to open database '%s'\n", dbstorage);
539
540 // open the database
541 DbErrorCheck (sqlite3_open(dbstorage, &brain->db));
542 }
543
544 // add/remove services
545 MkErrorCheck (MqServiceDelete (mqctx, "OPEN"));
546
547 MkErrorCheck (MqServiceCreate (mqctx, "CLOS", CLOS, NULL, NULL, NULL));
548 MkErrorCheck (MqServiceCreate (mqctx, "EXEC", EXEC, NULL, NULL, NULL));
549 MkErrorCheck (MqServiceCreate (mqctx, "PREP", PREP, NULL, NULL, NULL));
550 MkErrorCheck (MqServiceCreate (mqctx, "FINA", FINA, NULL, NULL, NULL));
551 MkErrorCheck (MqServiceCreate (mqctx, "STEP", STEP, NULL, NULL, NULL));
552
553 MqSendSTART(mqctx);
554error:
555 return MqSendRETURN(mqctx);
556}
static enum MkErrorE FINA(MQ_SERVICE_CALL_ARGS)
Definition abrain.c:507
static enum MkErrorE STEP(MQ_SERVICE_CALL_ARGS)
Definition abrain.c:302
static enum MkErrorE EXEC(MQ_SERVICE_CALL_ARGS)
Definition abrain.c:415
static enum MkErrorE PREP(MQ_SERVICE_CALL_ARGS)
Definition abrain.c:425
static enum MkErrorE CLOS(MQ_SERVICE_CALL_ARGS)
Definition abrain.c:517
#define MkErrorSetC_4M(m,...)
#define MkDLogV(x, _debug, printfmt,...)
#define MqSendSTART(...)
+ Here is the caller graph for this function:

◆ PREP()

static enum MkErrorE PREP ( MQ_SERVICE_CALL_ARGS )
static

Definition at line 425 of file abrain.c.

425 {
427 MK_STRN sql,end,type,start;
428 MK_I32 idx;
429 MK_BUF buf;
430
431 // parse prefix
432 MkErrorCheck(MqReadBUF(mqctx,&buf));
433 if (buf->var.type == MK_I32T) {
434 MkErrorCheck(MkBufferGetI32(buf,&idx));
435 MkErrorCheck(IdxFinalize(mqctx, idx));
436 MkErrorCheck(MqReadBUF(mqctx,&buf));
437 } else {
438 idx = brain->prepare_start;
439 }
440 MkErrorCheck(MkBufferGetSTR(buf,&sql));
441 end = sql + buf->storage.size;
442
443 // process values
444 MqSendSTART(mqctx);
445 while (sql != NULL && *sql != '\0') {
446 // get the index
447 for (; idx<DB_PREPARE_MAX && brain->prepStmt[idx]!=NULL; idx++);
448 if (idx >= DB_PREPARE_MAX) {
449 MkErrorSetV_4M (mqctx, __func__, SQLITE_ERROR, "unable to find a free prepare entry - only '%i' entries are allowed.", DB_PREPARE_MAX);
450 goto error;
451 }
452 // find 'in:???' prefix
453 brain->inType[idx] = NULL;
454 brain->inEnd[idx] = NULL;
455 brain->outType[idx] = NULL;
456 brain->outEnd[idx] = NULL;
457 // 1. search for '/' as beginn of comment
458 for (start=sql; start<end && *start != '/' && *start != ';'; start++);
459 // 2. '/*' as 2cnd char
460 if (start == end || *start++ != '/' || *start++ != '*') goto update;
461
462 // find 'in:???' prefix
463 // in1. 'WS' before "TYPE:???"
464 for (; start<end && isspace(*start); start++);
465 // in2. 'in:' the prefix
466 if (start >= end-3 || strncmp(start, "in:", 3)) goto out;
467 start+=3;
468 // in3. 'ASCII' as beginn of comment
469 for (type=start; start<end && isupper(*start); start++);
470 if (start == end) goto out;
471 // in4. we have everything
472 brain->inType[idx] = MkSysStrNDup(MkOBJ(mqctx), type, (start-type));
473 brain->inEnd[idx] = brain->inType[idx] + (start-type);
474 *brain->inEnd[idx] = '\0';
475
476out:
477 // find 'out:???' prefix
478 // out1. 'WS' before "TYPE:???"
479 for (; start<end && isspace(*start); start++);
480 // out2. 'out:' the prefix
481 if (start >= end-4 || strncmp(start, "out:", 4)) goto update;
482 start+=4;
483 // out3. 'ASCII' as beginn of comment
484 for (type=start; start<end && isupper(*start); start++);
485 if (start == end) goto update;
486 // out4. we have everything
487 brain->outType[idx] = MkSysStrNDup(MkOBJ(mqctx), type, (start-type));
488 brain->outEnd[idx] = brain->outType[idx] + (start-type);
489 *brain->outEnd[idx] = '\0';
490
491update:
492 // update the database
493 brain->prepare_start=idx+1;
494 DbErrorCheck(sqlite3_prepare_v2(brain->db, sql, -1, &brain->prepStmt[idx], &sql));
495 MqSendI32(mqctx, idx);
496 }
497error:
498/*
499printLC(brain->inType[idx])
500printLC(brain->inEnd[idx])
501printLC(brain->outType[idx])
502printLC(brain->outEnd[idx])
503*/
504 return MqSendRETURN(mqctx);
505}
#define MkBufferGetSTR(...)
#define MkBufferGetI32(...)
#define MkOBJ(x)
MK_STR MkSysStrNDup(MK_OBJN fmtobj, MK_STRN const str, MK_SIZE const len)
#define MqReadBUF(...)
struct MkBufferS::@5 storage
MK_NUM size
struct MkBufferS::@4 var
enum MkTypeE type
+ Here is the caller graph for this function:

◆ STEP()

static enum MkErrorE STEP ( MQ_SERVICE_CALL_ARGS )
static

Definition at line 302 of file abrain.c.

302 {
304 MK_I32 idx=0;
305 MK_BUF buf;
306 sqlite3_stmt *hdl=NULL;
307 MK_STRN inType=NULL, inEnd=NULL;
308 MK_STRN outType=NULL, outEnd=NULL;
309 enum MkTypeE ntype;
310
311 MkErrorCheck(HdlGet(mqctx, &hdl, &inType, &inEnd, &outType, &outEnd));
312 DbErrorCheck(sqlite3_reset(hdl));
313
314 MqSendSTART(mqctx);
315 while (MqReadItemExists(mqctx)) {
316 idx+=1;
317 MkErrorCheck(MqReadBUF(mqctx,&buf));
318 if (inType && inType < inEnd) {
319 ntype = GetTypeE(*inType);
320 if (buf->var.type != ntype && buf->var.type != MK_STRT) {
321 MkErrorSetV_4M(mqctx,__func__,SQLITE_ERROR,
322 "the buffer type '%c' does not match database type '%c'",
323 MkBufferGetType1(buf), *inType);
324 goto error;
325 }
326 inType++;
327 } else {
328 ntype = buf->var.type;
329 }
330 switch (buf->var.type) {
331 case MK_I8T: DbErrorCheck(sqlite3_bind_int(hdl,idx,buf->storage.first.A->I8)); break;
332 case MK_BOLT: DbErrorCheck(sqlite3_bind_int(hdl,idx,buf->storage.first.A->BOL)); break;
333 case MK_I16T: DbErrorCheck(sqlite3_bind_int(hdl,idx,buf->storage.first.A->I16)); break;
334 case MK_I32T: DbErrorCheck(sqlite3_bind_int(hdl,idx,buf->storage.first.A->I32)); break;
335 case MK_I64T: DbErrorCheck(sqlite3_bind_int64(hdl,idx,buf->storage.first.A->I64)); break;
336 case MK_FLTT: DbErrorCheck(sqlite3_bind_double(hdl,idx,buf->storage.first.A->FLT)); break;
337 case MK_DBLT: DbErrorCheck(sqlite3_bind_double(hdl,idx,buf->storage.first.A->DBL)); break;
338 case MK_STRT:
339 switch (ntype) {
340 case1(MK_I8,sqlite3_bind_int,I8)
341 case1(MK_BOL,sqlite3_bind_int,BOL)
342 case1(MK_I16,sqlite3_bind_int,I16)
343 case1(MK_I32,sqlite3_bind_int,I32)
344 case1(MK_I64,sqlite3_bind_int64,I64)
345 case1(MK_FLT,sqlite3_bind_double,FLT)
346 case1(MK_DBL,sqlite3_bind_double,DBL)
347 case MK_STRT:
348 DbErrorCheck(sqlite3_bind_text (hdl,idx,buf->storage.first.C,(int)buf->storage.size,SQLITE_TRANSIENT));
349 break;
350 case MK_BINT:
351 if (buf->storage.size == 0) {
352 DbErrorCheck (sqlite3_bind_null (hdl,idx));
353 } else {
354 DbErrorCheck (sqlite3_bind_blob (hdl,idx,buf->storage.first.B,(int)buf->storage.size,SQLITE_TRANSIENT));
355 }
356 break;
357 case MK_LSTT:
358 MkErrorSetV_4M (mqctx, __func__, SQLITE_ERROR, "invalid protocoll item '%c'", GetTypeS(ntype));
359 }
360 break;
361 case MK_BINT:
362 if (buf->storage.size == 0) {
363 DbErrorCheck (sqlite3_bind_null (hdl,idx));
364 } else {
365 DbErrorCheck (sqlite3_bind_blob (hdl,idx,buf->storage.first.B,(int)buf->storage.size,SQLITE_TRANSIENT));
366 }
367 break;
368 case MK_LSTT:
369 MkErrorSetV_4M (mqctx, __func__, SQLITE_ERROR, "invalid protocoll item '%c'", GetTypeS(ntype));
370 break;
371 }
372 }
373
374 MK_STRN pos;
375 MqSendSTART(mqctx);
376 while (true) {
377 switch (sqlite3_step(hdl)) {
378 case SQLITE_ROW: {
379 MqSendL_START(mqctx);
380 for (idx=0,pos=outType; idx<sqlite3_column_count(hdl); idx++,pos++) {
381 ntype = pos && pos < outEnd ? GetTypeE(*pos) : GetTypeD(hdl,idx);
382 switch (sqlite3_column_type(hdl,idx)) {
383 case SQLITE_INTEGER:
384 case SQLITE_FLOAT:
385 case SQLITE_NULL:
386 MkErrorCheck(GetFromDBnat(mqctx, ntype, hdl, idx));
387 break;
388 case SQLITE_BLOB:
389 case SQLITE_TEXT:
390 MkErrorCheck(GetFromDBary(mqctx, ntype, hdl, idx));
391 break;
392 }
393 }
394 MqSendL_END(mqctx);
395 continue;
396 break;
397 }
398 case SQLITE_DONE:
399 goto error;
400 case SQLITE_LOCKED:
401 case SQLITE_BUSY:
402 continue;
403 default:
404 MkErrorSetC_4M (mqctx, sqlite3_errmsg(brain->db), __func__, sqlite3_extended_errcode(brain->db));
405 DbErrorCheck(sqlite3_reset(hdl));
406 goto error;
407 }
408 }
409
410error:
411 sqlite3_reset(hdl);
412 return MqSendRETURN(mqctx);
413}
#define GetFromDBary(...)
Definition abrain.c:300
static enum MkTypeE GetTypeE(MK_STRB t)
Definition abrain.c:191
static enum MkTypeE GetTypeD(sqlite3_stmt *hdl, MK_I32 idx)
Definition abrain.c:223
#define GetFromDBnat(...)
Definition abrain.c:274
#define HdlGet(...)
Definition abrain.c:164
#define case1(t, f, c)
Definition abrain.c:243
#define MkBufferGetType1(...)
MkTypeE
bool MqReadItemExists(MQ_CTX const ctx)
#define MqSendL_START(...)
#define MqSendL_END(...)
union MkBufferU first
MK_STRN C
MK_ATO * A
MK_BIN B
+ Here is the caller graph for this function:

Variable Documentation

◆ BrainTT

MK_TYP BrainTT = NULL
static

link to the MqErrorS object

Definition at line 27 of file abrain.c.