Annotation of libaitsess/src/sess.c, revision 1.5.4.2

1.2       misho       1: /*************************************************************************
                      2: * (C) 2008 AITNET ltd - Sofia/Bulgaria - <misho@aitbg.com>
                      3: *  by Michael Pounov <misho@openbsd-bg.org>
                      4: *
                      5: * $Author: misho $
1.5.4.2 ! misho       6: * $Id: sess.c,v 1.5.4.1 2013/01/17 13:10:49 misho Exp $
1.2       misho       7: *
1.3       misho       8: **************************************************************************
                      9: The ELWIX and AITNET software is distributed under the following
                     10: terms:
                     11: 
                     12: All of the documentation and software included in the ELWIX and AITNET
                     13: Releases is copyrighted by ELWIX - Sofia/Bulgaria <info@elwix.org>
                     14: 
1.5.4.1   misho      15: Copyright 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2013
1.3       misho      16:        by Michael Pounov <misho@elwix.org>.  All rights reserved.
                     17: 
                     18: Redistribution and use in source and binary forms, with or without
                     19: modification, are permitted provided that the following conditions
                     20: are met:
                     21: 1. Redistributions of source code must retain the above copyright
                     22:    notice, this list of conditions and the following disclaimer.
                     23: 2. Redistributions in binary form must reproduce the above copyright
                     24:    notice, this list of conditions and the following disclaimer in the
                     25:    documentation and/or other materials provided with the distribution.
                     26: 3. All advertising materials mentioning features or use of this software
                     27:    must display the following acknowledgement:
                     28: This product includes software developed by Michael Pounov <misho@elwix.org>
                     29: ELWIX - Embedded LightWeight unIX and its contributors.
                     30: 4. Neither the name of AITNET nor the names of its contributors
                     31:    may be used to endorse or promote products derived from this software
                     32:    without specific prior written permission.
                     33: 
                     34: THIS SOFTWARE IS PROVIDED BY AITNET AND CONTRIBUTORS ``AS IS'' AND
                     35: ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
                     36: IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
                     37: ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
                     38: FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
                     39: DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
                     40: OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
                     41: HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
                     42: LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
                     43: OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
                     44: SUCH DAMAGE.
                     45: */
1.1       misho      46: #include "global.h"
                     47: 
                     48: 
                     49: /*
1.5.4.2 ! misho      50:  * sess_FreeValues() - Free all values from value array allocated from sess_GetValues()
1.4       misho      51:  *
1.2       misho      52:  * @ppsVals = Array strings
                     53:  * return: none
1.4       misho      54:  */
1.3       misho      55: inline void
                     56: sess_FreeValues(char *** __restrict ppsVals)
1.2       misho      57: {
                     58:        char **ptr;
                     59: 
1.3       misho      60:        assert(ppsVals);
                     61:        if (!ppsVals)
                     62:                return;
                     63: 
1.2       misho      64:        for (ptr = *ppsVals; *ptr; ptr++)
1.5.4.1   misho      65:                e_free(*ptr);
                     66:        e_free(*ppsVals);
1.2       misho      67:        *ppsVals = NULL;
                     68: }
                     69: 
                     70: /*
1.5.4.2 ! misho      71:  * sess_GetValues() - Get all values from session shared memory
1.4       misho      72:  *
1.2       misho      73:  * @s = Session item
                     74:  * @ppsVals = Return array strings
1.5.4.2 ! misho      75:  * return: -1 error: in parameter, !=-1 count of returned strings in ppsVals 
        !            76:  *             (must be sess_FreeValues after use!)
1.4       misho      77:  */
1.3       misho      78: int
1.4       misho      79: sess_GetValues(ait_sess_t * __restrict s, char ***ppsVals)
1.2       misho      80: {
                     81:        register int i;
                     82:        char **valz, *Shared = NULL;
                     83:        char *peer, *p_brk;
                     84: 
                     85:        if (!s || !ppsVals)
                     86:                return -1;
1.5.4.1   misho      87:        valz = e_malloc(sizeof(caddr_t));
1.2       misho      88:        if (!valz) {
                     89:                LOGERR;
                     90:                return -1;
                     91:        } else
                     92:                *valz = NULL;
                     93: 
1.5.4.2 ! misho      94:        /* allocated memory & mirrored shared memory into this */
1.5.4.1   misho      95:        Shared = e_malloc(s->eom);
1.2       misho      96:        if (!Shared) {
                     97:                LOGERR;
1.5.4.1   misho      98:                e_free(valz);
1.2       misho      99:                return -1;
                    100:        } else
                    101:                memcpy(Shared, s->addr, s->eom);
                    102: 
                    103:        for (i = 0, peer = strtok_r(Shared, MEM_DELIM"\r\n", &p_brk); peer; 
                    104:                        peer = strtok_r(NULL, MEM_DELIM"\r\n", &p_brk)) {
                    105:                if (!strchr(peer, '='))
                    106:                        continue;
                    107:                else
                    108:                        i++;
                    109: 
1.5.4.1   misho     110:                valz = e_realloc(valz, (i + 1) * sizeof(caddr_t));
1.2       misho     111:                if (!valz) {
                    112:                        LOGERR;
1.5.4.1   misho     113:                        e_free(Shared);
1.2       misho     114:                        return -1;
                    115:                } else
                    116:                        valz[i] = NULL;
                    117: 
1.5.4.1   misho     118:                valz[i - 1] = e_strdup(peer);
1.2       misho     119:        }
                    120: 
1.5.4.1   misho     121:        e_free(Shared);
1.2       misho     122:        *ppsVals = valz;
                    123:        return i;
                    124: }
                    125: 
                    126: /*
1.5.4.2 ! misho     127:  * sess_GetValue() - Get value from session shared memory from attribute
1.4       misho     128:  *
1.1       misho     129:  * @s = Session item
                    130:  * @csAttr = Attribute for search
                    131:  * @psVal = Return string buffer
                    132:  * @pnLen = Length of return string buffer, 
                    133:        // *{pnLen} input is max_size of buffer & output is really taken bytes
1.5.4.2 ! misho     134:  * return: 0 not found, -1 error: in parameter, >0 get position, 
        !           135:  *     if define item merged with IS_DEF
1.4       misho     136:  */
1.3       misho     137: int
1.4       misho     138: sess_GetValue(ait_sess_t * __restrict s, const char *csAttr, char *psVal, int *pnLen)
1.1       misho     139: {
                    140:        register int i;
                    141:        int def = IS_VAL;
                    142:        char *Shared = NULL;
                    143:        char *peer, *p_brk, *a_brk, *attr, *val;
                    144: 
                    145:        if (!s || !csAttr || !*csAttr)
                    146:                return -1;
                    147:        if (psVal) {
                    148:                if (pnLen && *pnLen > 0)
                    149:                        memset(psVal, 0, *pnLen);
                    150:                else
                    151:                        return -1;
                    152:        }
                    153: 
1.5.4.2 ! misho     154:        /* allocated memory & mirrored shared memory into this */
1.5.4.1   misho     155:        Shared = e_malloc(s->eom);
1.1       misho     156:        if (!Shared) {
                    157:                LOGERR;
                    158:                return -1;
                    159:        } else
                    160:                memcpy(Shared, s->addr, s->eom);
                    161: 
1.2       misho     162:        for (i = 1, peer = strtok_r(Shared, MEM_DELIM"\r\n", &p_brk); peer; 
                    163:                        i++, peer = strtok_r(NULL, MEM_DELIM"\r\n", &p_brk)) {
1.1       misho     164:                attr = strtok_r(peer, "=\r\n", &a_brk);
1.4       misho     165:                if (attr && !strncmp(attr, csAttr, MAX_ATTRIBUTE - 1)) {
1.1       misho     166:                        val = strtok_r(NULL, "=\r\n", &a_brk);
                    167:                        if (val && strlen(val)) {
                    168:                                if (psVal)
1.2       misho     169:                                        strlcpy(psVal, val, *pnLen);
1.1       misho     170:                                if (pnLen)
                    171:                                        *pnLen = strlen(val);
                    172:                        } else
                    173:                                def = IS_DEF;
                    174: 
1.5.4.1   misho     175:                        e_free(Shared);
1.1       misho     176:                        return i | def;
                    177:                }
                    178:        }
                    179: 
1.5.4.1   misho     180:        e_free(Shared);
1.1       misho     181:        return 0;
                    182: }
                    183: 
                    184: /*
1.5.4.2 ! misho     185:  * sess_DelValue() - Delete item from session shared memory
1.4       misho     186:  *
1.1       misho     187:  * @s = Session item
                    188:  * @csAttr = Attribute for erasing
                    189:  * return: 0 Ok, -1 error: in parameter
1.4       misho     190:  */
1.3       misho     191: int
1.4       misho     192: sess_DelValue(ait_sess_t * __restrict s, const char *csAttr)
1.1       misho     193: {
                    194:        register int i;
1.4       misho     195:        int attrlen;
                    196:        char *Buffer, *Shared, szAttr[MAX_ATTRIBUTE];
1.1       misho     197:        char *peer, *p_brk;
                    198: 
                    199:        if (!s || !csAttr || !*csAttr)
                    200:                return -1;
                    201:        else
                    202:                attrlen = strlen(csAttr);
                    203:        Buffer = Shared = NULL;
1.4       misho     204:        strlcpy(szAttr, csAttr, sizeof szAttr);
                    205:        strlcat(szAttr, "=", sizeof szAttr);
1.1       misho     206: 
1.5.4.1   misho     207:        Buffer = e_malloc(s->eom);
1.1       misho     208:        if (!Buffer) {
                    209:                LOGERR;
                    210:                return -1;
                    211:        } else
                    212:                memset(Buffer, 0, s->eom);
1.5.4.1   misho     213:        Shared = e_malloc(s->eom);
1.1       misho     214:        if (!Shared) {
                    215:                LOGERR;
1.5.4.1   misho     216:                e_free(Buffer);
1.1       misho     217:                return -1;
                    218:        } else {
1.4       misho     219:                DEC_SEM(s);
1.1       misho     220:                memcpy(Shared, s->addr, s->eom);
                    221:        }
                    222: 
1.2       misho     223:        for (i = 1, peer = strtok_r(Shared, MEM_DELIM"\r\n", &p_brk); peer; 
                    224:                        i++, peer = strtok_r(NULL, MEM_DELIM"\r\n", &p_brk)) {
1.1       misho     225:                if (!strncmp(peer, csAttr, attrlen))
1.2       misho     226:                        if (peer[attrlen] == '=' || peer[attrlen] == *MEM_DELIM || !peer[attrlen] ||
1.1       misho     227:                                        peer[attrlen] == '\r' || peer[attrlen] == '\n')
                    228:                                continue;
                    229: 
1.4       misho     230:                strlcat(Buffer, peer, s->eom);
                    231:                strlcat(Buffer, MEM_DELIM, s->eom);
1.1       misho     232:        }
                    233: 
                    234:        memcpy(s->addr, Buffer, s->eom);
                    235: 
                    236:        if (s->type == SHARED_MAP)
                    237:                msync(s->addr, 0, MS_SYNC | MS_INVALIDATE);
                    238: 
1.4       misho     239:        INC_SEM(s);
1.5.4.1   misho     240:        e_free(Shared);
                    241:        e_free(Buffer);
1.1       misho     242:        return 0;
                    243: }
                    244: 
                    245: /*
1.5.4.2 ! misho     246:  * sess_SetValue() - Set item into session shared memory or update if exists
1.4       misho     247:  *
1.1       misho     248:  * @s = Session item
                    249:  * @csAttr = Attribute
                    250:  * @psVal = Value
                    251:  * return: 0 nothing, -1 error: in parameter, 
                    252:        >0 set position, if add item merged with IS_ADD and if define item merged with IS_DEF
1.4       misho     253:  */
1.3       misho     254: int
1.4       misho     255: sess_SetValue(ait_sess_t * __restrict s, const char *csAttr, const char *psVal)
1.1       misho     256: {
                    257:        register int i;
1.4       misho     258:        int upd, def = IS_VAL;
                    259:        char *Buffer, *Shared, szAttr[MAX_ATTRIBUTE];
1.1       misho     260:        char *peer, *p_brk;
                    261: 
                    262:        if (!s || !csAttr || !*csAttr)
                    263:                return -1;
                    264:        else
                    265:                Buffer = Shared = NULL;
1.4       misho     266:        strlcpy(szAttr, csAttr, sizeof szAttr);
                    267:        strlcat(szAttr, "=", sizeof szAttr);
1.1       misho     268: 
1.5.4.1   misho     269:        Buffer = e_malloc(s->eom);
1.1       misho     270:        if (!Buffer) {
                    271:                LOGERR;
                    272:                return -1;
                    273:        } else
                    274:                memset(Buffer, 0, s->eom);
1.5.4.1   misho     275:        Shared = e_malloc(s->eom);
1.1       misho     276:        if (!Shared) {
                    277:                LOGERR;
1.5.4.1   misho     278:                e_free(Buffer);
1.1       misho     279:                return -1;
                    280:        } else {
1.4       misho     281:                DEC_SEM(s);
1.1       misho     282:                memcpy(Shared, s->addr, s->eom);
                    283:        }
                    284: 
1.2       misho     285:        for (i = 1, upd = 0, peer = strtok_r(Shared, MEM_DELIM"\r\n", &p_brk); peer; 
                    286:                        i++, peer = strtok_r(NULL, MEM_DELIM"\r\n", &p_brk)) {
1.1       misho     287:                if (!strncmp(peer, szAttr, strlen(szAttr))) {
                    288:                        upd++;
                    289:                        if (psVal) {
1.4       misho     290:                                strlcat(Buffer, szAttr, s->eom);
                    291:                                strlcat(Buffer, psVal, s->eom);
                    292:                                strlcat(Buffer, MEM_DELIM, s->eom);
1.1       misho     293:                        } else {
1.4       misho     294:                                strlcat(Buffer, csAttr, s->eom);
                    295:                                strlcat(Buffer, MEM_DELIM, s->eom);
1.1       misho     296:                                def = IS_DEF;
                    297:                        }
                    298:                        continue;
                    299:                }
                    300: 
1.4       misho     301:                strlcat(Buffer, peer, s->eom);
                    302:                strlcat(Buffer, MEM_DELIM, s->eom);
1.1       misho     303:        }
                    304: 
                    305:        if (!upd) {
                    306:                if (psVal) {
1.4       misho     307:                        strlcat(Buffer, szAttr, s->eom);
                    308:                        strlcat(Buffer, psVal, s->eom);
                    309:                        strlcat(Buffer, MEM_DELIM, s->eom);
1.1       misho     310:                } else {
1.4       misho     311:                        strlcat(Buffer, csAttr, s->eom);
                    312:                        strlcat(Buffer, MEM_DELIM, s->eom);
1.1       misho     313:                        def = IS_DEF;
                    314:                }
                    315:                def |= IS_ADD;
                    316:        }
                    317: 
                    318:        memcpy(s->addr, Buffer, s->eom);
                    319: 
                    320:        if (s->type == SHARED_MAP)
                    321:                msync(s->addr, 0, MS_SYNC | MS_INVALIDATE);
                    322: 
1.4       misho     323:        INC_SEM(s);
1.5.4.1   misho     324:        e_free(Shared);
                    325:        e_free(Buffer);
1.1       misho     326:        return upd | def;
                    327: }
1.4       misho     328: 
                    329: 
                    330: /*
1.5.4.2 ! misho     331:  * sess_prepareSession() - Attach to shared memory and de-marshaling data
1.4       misho     332:  *
                    333:  * @s = Session
                    334:  * @useDirect = Use direct shared memory if !=0 or snapshot of data to array
                    335:  * return: NULL error or no data, !=NULL array with variables, 
                    336:  *             after use must free resources with sess_doneSession()
                    337:  */
                    338: array_t *
                    339: sess_prepareSession(ait_sess_t * __restrict s, char useDirect)
                    340: {
                    341:        array_t *arr = NULL;
                    342:        sess_hdr_t *hdr;
                    343: 
                    344:        assert(s);
                    345:        if (!s) {
1.5.4.2 ! misho     346:                sess_SetErr(EINVAL, "Invalid argument\n");
1.4       misho     347:                return NULL;
                    348:        }
                    349:        if (s->addr) {
1.5.4.2 ! misho     350:                sess_SetErr(EINVAL, "Already attached memory\n");
1.4       misho     351:                return NULL;
                    352:        }
                    353: 
                    354:        ATTACH_MEMORY(s);
                    355:        if (!s->addr)
                    356:                return NULL;
                    357:        else
                    358:                hdr = (sess_hdr_t*) s->addr;
                    359:        if (hdr->hdr_magic != SESS_AIT_MAGIC) {
                    360:                DETACH_MEMORY(s);
                    361: 
1.5.4.2 ! misho     362:                sess_SetErr(EINVAL, "Shared memory not contains values with proper format\n");
1.4       misho     363:                return NULL;
                    364:        }
                    365: 
                    366:        DEC_SEM(s);
                    367:        s->zcpy = useDirect;
1.5.4.1   misho     368:        arr = ait_map2vars(s->addr + sizeof(sess_hdr_t), s->eom - sizeof(sess_hdr_t), 
1.4       misho     369:                        hdr->hdr_argc, useDirect);
                    370:        INC_SEM(s);
                    371: 
                    372:        if (!s->zcpy)
                    373:                DETACH_MEMORY(s);
                    374:        return arr;
                    375: }
                    376: 
                    377: /*
1.5.4.2 ! misho     378:  * sess_doneSession() - Free resources allocated with sess_prepareSession()
1.4       misho     379:  *
                    380:  * @s = Session
                    381:  * @arr = Array with variables for free
                    382:  * return: none
                    383:  */
                    384: void
                    385: sess_doneSession(ait_sess_t * __restrict s, array_t ** __restrict arr)
                    386: {
                    387:        assert(s);
                    388:        if (!s) {
1.5.4.2 ! misho     389:                sess_SetErr(EINVAL, "Invalid argument\n");
1.4       misho     390:                return;
                    391:        }
                    392: 
                    393:        if (!s->zcpy)
1.5.4.1   misho     394:                array_Free(*arr);
1.4       misho     395:        else
                    396:                DETACH_MEMORY(s);
1.5.4.1   misho     397:        array_Destroy(arr);
1.4       misho     398: }
                    399: 
                    400: /*
1.5.4.2 ! misho     401:  * sess_commitSession() - Commit data to shared memory
1.4       misho     402:  *
                    403:  * @s = Session
                    404:  * @arr = Array with variables for save
                    405:  * return -1 error or !=-1 size of stored variables into shared memory
                    406:  */
                    407: int
                    408: sess_commitSession(ait_sess_t * __restrict s, array_t * __restrict arr)
                    409: {
                    410:        sess_hdr_t *hdr;
                    411:        int ret = 0;
                    412: 
                    413:        assert(s && arr);
                    414:        if (!s || !arr) {
1.5.4.2 ! misho     415:                sess_SetErr(EINVAL, "Invalid argument\n");
1.4       misho     416:                return -1;
                    417:        }
                    418: 
                    419:        ATTACH_MEMORY(s);
                    420:        if (!s->addr) {
                    421:                DETACH_MEMORY(s);
                    422:                return -1;
                    423:        } else
                    424:                hdr = (sess_hdr_t*) s->addr;
                    425: 
                    426:        DEC_SEM(s);
1.5.4.1   misho     427:        if ((ret = ait_vars2map(s->addr + sizeof(sess_hdr_t), 
                    428:                                        s->eom - sizeof(sess_hdr_t), arr)) != -1) {
1.4       misho     429:                hdr->hdr_magic = SESS_AIT_MAGIC;
1.5.4.1   misho     430:                hdr->hdr_argc = array_Size(arr);
1.4       misho     431:                ret += sizeof(sess_hdr_t);
                    432:        }
                    433:        INC_SEM(s);
                    434: 
                    435:        DETACH_MEMORY(s);
                    436:        return ret;
                    437: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>