Changeset bff8619 in mainline for uspace/srv/volsrv/volume.c


Ignore:
Timestamp:
2024-08-20T22:07:31Z (9 months ago)
Author:
Jiri Svoboda <jiri@…>
Branches:
master
Children:
ac9b4f2
Parents:
a3ba37d
Message:

Simplify SIF interface, remove contacts

Remove transactions, move to a load/save model. Remove contacts
application as it was never finished and not useful at all.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/srv/volsrv/volume.c

    ra3ba37d rbff8619  
    11/*
    2  * Copyright (c) 2018 Jiri Svoboda
     2 * Copyright (c) 2024 Jiri Svoboda
    33 * All rights reserved.
    44 *
     
    4848#include <fibril_synch.h>
    4949#include <io/log.h>
     50#include <sif.h>
    5051#include <stdbool.h>
    5152#include <stdlib.h>
     
    6061    vol_volume_t **);
    6162static errno_t vol_volumes_load(sif_node_t *, vol_volumes_t *);
     63static errno_t vol_volumes_save(vol_volumes_t *, sif_node_t *);
    6264
    6365/** Allocate new volume structure.
     
    113115{
    114116        vol_volumes_t *volumes;
    115         sif_sess_t *repo = NULL;
    116         sif_trans_t *trans = NULL;
     117        sif_doc_t *doc = NULL;
    117118        sif_node_t *node;
     119        sif_node_t *nvolumes;
    118120        const char *ntype;
    119121        errno_t rc;
     
    123125                return ENOMEM;
    124126
     127        volumes->cfg_path = str_dup(cfg_path);
     128        if (volumes->cfg_path == NULL) {
     129                rc = ENOMEM;
     130                goto error;
     131        }
     132
    125133        fibril_mutex_initialize(&volumes->lock);
    126134        list_initialize(&volumes->volumes);
     
    128136
    129137        /* Try opening existing repository */
    130         rc = sif_open(cfg_path, &repo);
     138        rc = sif_load(cfg_path, &doc);
    131139        if (rc != EOK) {
    132140                /* Failed to open existing, create new repository */
    133                 rc = sif_create(cfg_path, &repo);
     141                rc = sif_new(&doc);
    134142                if (rc != EOK)
    135143                        goto error;
    136144
    137                 rc = sif_trans_begin(repo, &trans);
     145                /* Create 'volumes' node. */
     146                rc = sif_node_append_child(sif_get_root(doc), "volumes",
     147                    &nvolumes);
    138148                if (rc != EOK)
    139149                        goto error;
    140150
    141                 /* Create 'volumes' node. */
    142                 rc = sif_node_append_child(trans, sif_get_root(repo),
    143                     "volumes", &volumes->nvolumes);
     151                rc = sif_save(doc, cfg_path);
    144152                if (rc != EOK)
    145153                        goto error;
    146154
    147                 rc = sif_trans_end(trans);
    148                 if (rc != EOK)
    149                         goto error;
    150 
    151                 trans = NULL;
     155                sif_delete(doc);
    152156        } else {
    153157                /*
    154                  * Opened existing repo. Find 'volumes' node, should be
    155                  * the first child of the root node.
     158                 * Loaded existing configuration. Find 'volumes' node, should
     159                 * be the first child of the root node.
    156160                 */
    157                 node = sif_node_first_child(sif_get_root(repo));
     161                node = sif_node_first_child(sif_get_root(doc));
    158162
    159163                /* Verify it's the correct node type */
     
    167171                if (rc != EOK)
    168172                        goto error;
    169         }
    170 
    171         volumes->repo = repo;
     173
     174                sif_delete(doc);
     175        }
     176
    172177        *rvolumes = volumes;
    173 
    174178        return EOK;
    175179error:
    176         if (trans != NULL)
    177                 sif_trans_abort(trans);
    178         if (repo != NULL)
    179                 (void) sif_close(repo);
     180        if (doc != NULL)
     181                (void) sif_delete(doc);
     182        if (volumes != NULL && volumes->cfg_path != NULL)
     183                free(volumes->cfg_path);
    180184        if (volumes != NULL)
    181185                free(volumes);
    182186
     187        return rc;
     188}
     189
     190/** Sync volume configuration to config file.
     191 *
     192 * @param volumes List of volumes
     193 * @return EOK on success, ENOMEM if out of memory
     194 */
     195errno_t vol_volumes_sync(vol_volumes_t *volumes)
     196{
     197        sif_doc_t *doc = NULL;
     198        errno_t rc;
     199
     200        rc = sif_new(&doc);
     201        if (rc != EOK)
     202                goto error;
     203
     204        rc = vol_volumes_save(volumes, sif_get_root(doc));
     205        if (rc != EOK)
     206                goto error;
     207
     208        rc = sif_save(doc, volumes->cfg_path);
     209        if (rc != EOK)
     210                goto error;
     211
     212        sif_delete(doc);
     213        return EOK;
     214error:
     215        if (doc != NULL)
     216                (void) sif_delete(doc);
    183217        return rc;
    184218}
     
    206240        }
    207241
    208         (void) sif_close(volumes->repo);
     242        free(volumes->cfg_path);
    209243        free(volumes);
    210244}
     
    383417        char *mp;
    384418        char *old_mp;
    385         errno_t rc;
    386         sif_trans_t *trans = NULL;
    387         sif_node_t *nvolume;
     419        bool was_persist;
    388420
    389421        mp = str_dup(mountp);
     
    391423                return ENOMEM;
    392424
     425        was_persist = vol_volume_is_persist(volume);
     426
    393427        old_mp = volume->mountp;
    394428        volume->mountp = mp;
    395429
    396430        if (vol_volume_is_persist(volume)) {
    397                 /* Volume is now persistent */
    398                 if (volume->nvolume == NULL) {
    399                         /* Prevent volume from being freed */
     431                if (!was_persist) {
     432                        /*
     433                         * Volume is now persistent. Prevent it from being
     434                         * freed.
     435                         */
    400436                        refcount_up(&volume->refcnt);
    401 
    402                         /* Create volume node */
    403                         rc = sif_trans_begin(volume->volumes->repo, &trans);
    404                         if (rc != EOK)
    405                                 goto error;
    406 
    407                         rc = sif_node_append_child(trans,
    408                             volume->volumes->nvolumes, "volume", &nvolume);
    409                         if (rc != EOK)
    410                                 goto error;
    411 
    412                         rc = sif_node_set_attr(trans, nvolume, "label",
    413                             volume->label);
    414                         if (rc != EOK)
    415                                 goto error;
    416 
    417                         rc = sif_node_set_attr(trans, nvolume, "mountp",
    418                             volume->mountp);
    419                         if (rc != EOK)
    420                                 goto error;
    421 
    422                         rc = sif_trans_end(trans);
    423                         if (rc != EOK)
    424                                 goto error;
    425 
    426                         trans = NULL;
    427                         volume->nvolume = nvolume;
    428                 } else {
    429                         /* Allow volume to be freed */
     437                }
     438        } else {
     439                if (was_persist) {
     440                        /*
     441                         * Volume is now non-persistent
     442                         * Allow volume to be freed.
     443                         */
    430444                        vol_volume_del_ref(volume);
    431 
    432                         /* Update volume node */
    433                         rc = sif_trans_begin(volume->volumes->repo, &trans);
    434                         if (rc != EOK)
    435                                 goto error;
    436 
    437                         rc = sif_node_set_attr(trans, volume->nvolume,
    438                             "mountp", volume->mountp);
    439                         if (rc != EOK)
    440                                 goto error;
    441 
    442                         rc = sif_trans_end(trans);
    443                         if (rc != EOK)
    444                                 goto error;
    445 
    446                         trans = NULL;
    447                 }
    448         } else {
    449                 /* Volume is now non-persistent */
    450                 if (volume->nvolume != NULL) {
    451                         /* Delete volume node */
    452                         rc = sif_trans_begin(volume->volumes->repo, &trans);
    453                         if (rc != EOK)
    454                                 goto error;
    455 
    456                         sif_node_destroy(trans, volume->nvolume);
    457 
    458                         rc = sif_trans_end(trans);
    459                         if (rc != EOK)
    460                                 goto error;
    461 
    462                         volume->nvolume = NULL;
    463                 }
    464         }
    465 
     445                }
     446        }
     447
     448        vol_volumes_sync(volume->volumes);
    466449        free(old_mp);
    467450        return EOK;
    468 error:
    469         free(mp);
    470         volume->mountp = old_mp;
    471 
    472         if (trans != NULL)
    473                 sif_trans_abort(trans);
    474         return rc;
    475451}
    476452
     
    521497}
    522498
    523 /** Load volumes from SIF repository.
     499/** Load volumes from SIF document.
    524500 *
    525501 * @param nvolumes Volumes node
     
    536512        errno_t rc;
    537513
    538         volumes->nvolumes = nvolumes;
    539 
    540514        nvolume = sif_node_first_child(nvolumes);
    541515        while (nvolume != NULL) {
     
    565539                volume->mountp = str_dup(mountp);
    566540
    567                 volume->nvolume = nvolume;
    568541                fibril_mutex_lock(&volumes->lock);
    569542                vol_volume_add_locked(volumes, volume);
     
    579552}
    580553
     554/** Save volumes to SIF document.
     555 *
     556 * @param volumes List of volumes
     557 * @param rnode Configuration root node
     558 * @return EOK on success, ENOMEM if out of memory
     559 */
     560errno_t vol_volumes_save(vol_volumes_t *volumes, sif_node_t *rnode)
     561{
     562        sif_node_t *nvolumes;
     563        sif_node_t *node;
     564        link_t *link;
     565        vol_volume_t *volume;
     566        errno_t rc;
     567
     568        /* Create 'volumes' node. */
     569        rc = sif_node_append_child(rnode, "volumes", &nvolumes);
     570        if (rc != EOK)
     571                goto error;
     572
     573        link = list_first(&volumes->volumes);
     574        while (link != NULL) {
     575                volume = list_get_instance(link, vol_volume_t, lvolumes);
     576
     577                if (vol_volume_is_persist(volume)) {
     578                        /* Create 'volume' node. */
     579                        rc = sif_node_append_child(rnode, "volume", &node);
     580                        if (rc != EOK)
     581                                goto error;
     582
     583                        rc = sif_node_set_attr(node, "label", volume->label);
     584                        if (rc != EOK)
     585                                goto error;
     586
     587                        rc = sif_node_set_attr(node, "mountp", volume->mountp);
     588                        if (rc != EOK)
     589                                goto error;
     590                }
     591
     592                link = list_next(&volume->lvolumes, &volumes->volumes);
     593        }
     594
     595        return EOK;
     596error:
     597        return rc;
     598}
     599
    581600/** Get volume information.
    582601 *
Note: See TracChangeset for help on using the changeset viewer.