LCOV - code coverage report
Current view: top level - libgfs2 - misc.c (source / functions) Coverage Total Hit
Test: gfs2-utils.info Lines: 29.9 % 97 29
Test Date: 2024-03-07 16:24:06 Functions: 33.3 % 6 2

            Line data    Source code
       1              : #include "clusterautoconfig.h"
       2              : 
       3              : #include <string.h>
       4              : #include <inttypes.h>
       5              : #include <sys/types.h>
       6              : #include <sys/stat.h>
       7              : #include <fcntl.h>
       8              : #include <unistd.h>
       9              : #include <time.h>
      10              : 
      11              : #include "libgfs2.h"
      12              : 
      13              : #define PAGE_SIZE (4096)
      14              : #define DIV_RU(x, y) (((x) + (y) - 1) / (y))
      15              : 
      16         9236 : int lgfs2_compute_heightsize(unsigned bsize, uint64_t *heightsize,
      17              :         uint32_t *maxheight, uint32_t bsize1, int diptrs, int inptrs)
      18              : {
      19         9236 :         heightsize[0] = bsize - sizeof(struct gfs2_dinode);
      20         9236 :         heightsize[1] = (uint64_t)bsize1 * diptrs;
      21         9236 :         for (*maxheight = 2;; (*maxheight)++) {
      22              :                 uint64_t space, d;
      23              :                 uint32_t m;
      24              : 
      25        46398 :                 space = heightsize[*maxheight - 1] * inptrs;
      26        46398 :                 m = space % inptrs;
      27        46398 :                 d = space / inptrs;
      28              : 
      29        46398 :                 if (d != heightsize[*maxheight - 1] || m)
      30              :                         break;
      31        37162 :                 heightsize[*maxheight] = space;
      32              :         }
      33         9236 :         if (*maxheight > GFS2_MAX_META_HEIGHT) {
      34            0 :                 errno = EINVAL;
      35            0 :                 return -1;
      36              :         }
      37         9236 :         return 0;
      38              : }
      39              : 
      40         4618 : int lgfs2_compute_constants(struct lgfs2_sbd *sdp)
      41              : {
      42         4618 :         sdp->md.next_inum = 1;
      43         4618 :         sdp->sd_time = time(NULL);
      44              : 
      45         4618 :         sdp->sd_bsize_shift = ffs(sdp->sd_bsize) - 1;
      46         4618 :         sdp->sd_fsb2bb_shift = sdp->sd_bsize_shift -
      47              :                 GFS2_BASIC_BLOCK_SHIFT;
      48         4618 :         sdp->sd_fsb2bb = 1 << sdp->sd_fsb2bb_shift;
      49         4618 :         sdp->sd_diptrs = (sdp->sd_bsize - sizeof(struct gfs2_dinode)) /
      50              :                 sizeof(uint64_t);
      51         4618 :         sdp->sd_inptrs = (sdp->sd_bsize - sizeof(struct gfs2_meta_header)) /
      52              :                 sizeof(uint64_t);
      53         4618 :         sdp->sd_jbsize = sdp->sd_bsize - sizeof(struct gfs2_meta_header);
      54         4618 :         sdp->sd_hash_bsize = sdp->sd_bsize / 2;
      55         4618 :         sdp->sd_hash_bsize_shift = sdp->sd_bsize_shift - 1;
      56         4618 :         sdp->sd_hash_ptrs = sdp->sd_hash_bsize / sizeof(uint64_t);
      57         4618 :         sdp->sd_blocks_per_bitmap = (sdp->sd_bsize - sizeof(struct gfs2_meta_header))
      58              :                                      * GFS2_NBBY;
      59              : 
      60         4618 :         if (lgfs2_compute_heightsize(sdp->sd_bsize, sdp->sd_heightsize, &sdp->sd_max_height,
      61         4618 :                                 sdp->sd_bsize, sdp->sd_diptrs, sdp->sd_inptrs)) {
      62            0 :                 return -1;
      63              :         }
      64         4618 :         if (lgfs2_compute_heightsize(sdp->sd_bsize, sdp->sd_jheightsize, &sdp->sd_max_jheight,
      65         4618 :                                 sdp->sd_jbsize, sdp->sd_diptrs, sdp->sd_inptrs)) {
      66            0 :                 return -1;
      67              :         }
      68         4618 :         return 0;
      69              : }
      70              : 
      71              : /* Returns 0 if fd1 and fd2 refer to the same device/file, 1 otherwise, or -1 on error */
      72            0 : static int fdcmp(int fd1, int fd2)
      73              : {
      74              :         struct stat st1, st2;
      75              : 
      76            0 :         if (fd1 < 0 || fd2 < 0)
      77            0 :                 return -1;
      78            0 :         if ((fstat(fd1, &st1) != 0) || (fstat(fd2, &st2) != 0))
      79            0 :                 return -1;
      80            0 :         if (S_ISBLK(st1.st_mode) && S_ISBLK(st2.st_mode)) {
      81            0 :                 if (st1.st_rdev == st2.st_rdev) {
      82            0 :                         return 0;
      83              :                 }
      84            0 :         } else if ((st1.st_dev == st2.st_dev) && (st1.st_ino == st2.st_ino)) {
      85            0 :                         return 0;
      86              :         }
      87            0 :         return 1;
      88              : }
      89              : 
      90            0 : int lgfs2_open_mnt(const char *path, int dirflags, int *dirfd, int devflags, int *devfd, struct mntent **mnt)
      91              : {
      92            0 :         FILE *fp = setmntent("/proc/mounts", "r");
      93            0 :         if (fp == NULL) {
      94            0 :                 perror("open: /proc/mounts");
      95            0 :                 return 1;
      96              :         }
      97              :         /* Assume path is mount point until we know better. */
      98            0 :         *dirfd = open(path, dirflags);
      99            0 :         if (*dirfd < 0)
     100            0 :                 return 1;
     101              : 
     102            0 :         while ((*mnt = getmntent(fp)) != NULL) {
     103              :                 int fd;
     104            0 :                 if (strcmp((*mnt)->mnt_type, "gfs2") != 0)
     105            0 :                         continue;
     106            0 :                 *devfd = open((*mnt)->mnt_fsname, devflags);
     107              :                 /* Defer checking *devfd until later: whether it's ok to ignore
     108              :                  * the error depends on whether we find the mount point. */
     109              : 
     110            0 :                 if (strcmp(path, (*mnt)->mnt_dir) == 0)
     111            0 :                         break;
     112            0 :                 if (strcmp(path, (*mnt)->mnt_fsname) == 0 || fdcmp(*dirfd, *devfd) == 0) {
     113              :                         /* We have a match but our above assumption was
     114              :                            incorrect and *dirfd is actually the device. */
     115            0 :                         close(*dirfd);
     116            0 :                         *dirfd = open((*mnt)->mnt_dir, dirflags);
     117            0 :                         break;
     118              :                 }
     119              : 
     120            0 :                 fd = open((*mnt)->mnt_dir, dirflags);
     121            0 :                 if (fd >= 0) {
     122            0 :                         int diff = fdcmp(*dirfd, fd);
     123            0 :                         close(fd);
     124            0 :                         if (diff == 0)
     125            0 :                                 break;
     126              :                 }
     127            0 :                 if (*devfd >= 0)
     128            0 :                         close(*devfd);
     129              :         }
     130            0 :         endmntent(fp);
     131            0 :         if (*mnt == NULL) {
     132            0 :                 close(*dirfd);
     133            0 :                 return 0; /* Success. Answer is no. Both fds closed. */
     134              :         }
     135            0 :         if (*dirfd < 0) {
     136            0 :                 close(*devfd);
     137            0 :                 return 1;
     138              :         }
     139            0 :         if (*devfd < 0) {
     140            0 :                 close(*dirfd);
     141            0 :                 return 1;
     142              :         }
     143            0 :         return 0; /* Success. Answer is yes. Both fds open. */
     144              : }
     145              : 
     146            0 : int lgfs2_open_mnt_dev(const char *path, int flags, struct mntent **mnt)
     147              : {
     148            0 :         int dirfd = -1;
     149            0 :         int devfd = -1;
     150            0 :         if (lgfs2_open_mnt(path, O_RDONLY, &dirfd, flags, &devfd, mnt) != 0)
     151            0 :                 return -1;
     152            0 :         if (*mnt != NULL)
     153            0 :                 close(dirfd);
     154            0 :         return devfd;
     155              : }
     156              : 
     157            0 : int lgfs2_open_mnt_dir(const char *path, int flags, struct mntent **mnt)
     158              : {
     159            0 :         int dirfd = -1;
     160            0 :         int devfd = -1;
     161            0 :         if (lgfs2_open_mnt(path, flags, &dirfd, O_RDONLY, &devfd, mnt) != 0)
     162            0 :                 return -1;
     163            0 :         if (*mnt != NULL)
     164            0 :                 close(devfd);
     165            0 :         return dirfd;
     166              : }
        

Generated by: LCOV version 2.0-1