]> git.kernelconcepts.de Git - karo-tx-linux.git/blobdiff - fs/gfs2/eattr.c
[GFS2] selinux support
[karo-tx-linux.git] / fs / gfs2 / eattr.c
index 63a5cf1e24729c3aedc18e6c40deb98aa1a36e5f..187fba1c4678f61adb54476ef372be58f0213f9a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  * Copyright (C) Sistina Software, Inc.  1997-2003 All rights reserved.
- * Copyright (C) 2004-2005 Red Hat, Inc.  All rights reserved.
+ * Copyright (C) 2004-2006 Red Hat, Inc.  All rights reserved.
  *
  * This copyrighted material is made available to anyone wishing to use,
  * modify, copy, or redistribute it subject to the terms and conditions
 #include <linux/completion.h>
 #include <linux/buffer_head.h>
 #include <linux/xattr.h>
-#include <asm/semaphore.h>
+#include <linux/gfs2_ondisk.h>
 #include <asm/uaccess.h>
 
 #include "gfs2.h"
+#include "lm_interface.h"
+#include "incore.h"
 #include "acl.h"
 #include "eaops.h"
 #include "eattr.h"
@@ -26,6 +28,7 @@
 #include "quota.h"
 #include "rgrp.h"
 #include "trans.h"
+#include "util.h"
 
 /**
  * ea_calc_size - returns the acutal number of bytes the request will take up
@@ -268,7 +271,7 @@ static int ea_dealloc_unstuffed(struct gfs2_inode *ip, struct buffer_head *bh,
        if (error)
                goto out_gunlock;
 
-       gfs2_trans_add_bh(ip->i_gl, bh);
+       gfs2_trans_add_bh(ip->i_gl, bh, 1);
 
        dataptrs = GFS2_EA2DATAPTRS(ea);
        for (x = 0; x < ea->ea_num_ptrs; x++, dataptrs++) {
@@ -309,7 +312,7 @@ static int ea_dealloc_unstuffed(struct gfs2_inode *ip, struct buffer_head *bh,
        error = gfs2_meta_inode_buffer(ip, &dibh);
        if (!error) {
                ip->i_di.di_ctime = get_seconds();
-               gfs2_trans_add_bh(ip->i_gl, dibh);
+               gfs2_trans_add_bh(ip->i_gl, dibh, 1);
                gfs2_dinode_out(&ip->i_di, dibh->b_data);
                brelse(dibh);
        }
@@ -354,31 +357,6 @@ static int ea_remove_unstuffed(struct gfs2_inode *ip, struct buffer_head *bh,
        return error;
 }
 
-/******************************************************************************/
-
-static int gfs2_ea_repack_i(struct gfs2_inode *ip)
-{
-       return -EOPNOTSUPP;
-}
-
-int gfs2_ea_repack(struct gfs2_inode *ip)
-{
-       struct gfs2_holder gh;
-       int error;
-
-       error = gfs2_glock_nq_init(ip->i_gl, LM_ST_EXCLUSIVE, 0, &gh);
-       if (error)
-               return error;
-
-       /* Some sort of permissions checking would be nice */
-
-       error = gfs2_ea_repack_i(ip);
-
-       gfs2_glock_dq_uninit(&gh);
-
-       return error;
-}
-
 struct ea_list {
        struct gfs2_ea_request *ei_er;
        unsigned int ei_size;
@@ -390,7 +368,7 @@ static int ea_list_i(struct gfs2_inode *ip, struct buffer_head *bh,
 {
        struct ea_list *ei = private;
        struct gfs2_ea_request *er = ei->ei_er;
-       unsigned int ea_size = GFS2_EA_STRLEN(ea);
+       unsigned int ea_size = gfs2_ea_strlen(ea);
 
        if (ea->ea_type == GFS2_EATYPE_UNUSED)
                return 0;
@@ -403,12 +381,21 @@ static int ea_list_i(struct gfs2_inode *ip, struct buffer_head *bh,
                if (ei->ei_size + ea_size > er->er_data_len)
                        return -ERANGE;
 
-               if (ea->ea_type == GFS2_EATYPE_USR) {
+               switch (ea->ea_type) {
+               case GFS2_EATYPE_USR:
                        prefix = "user.";
                        l = 5;
-               } else {
+                       break;
+               case GFS2_EATYPE_SYS:
                        prefix = "system.";
                        l = 7;
+                       break;
+               case GFS2_EATYPE_SECURITY:
+                       prefix = "security.";
+                       l = 9;
+                       break;
+               default:
+                       break;
                }
 
                memcpy(er->er_data + ei->ei_size,
@@ -479,7 +466,7 @@ static int ea_get_unstuffed(struct gfs2_inode *ip, struct gfs2_ea_header *ea,
        struct gfs2_sbd *sdp = ip->i_sbd;
        struct buffer_head **bh;
        unsigned int amount = GFS2_EA_DATA_LEN(ea);
-       unsigned int nptrs = DIV_RU(amount, sdp->sd_jbsize);
+       unsigned int nptrs = DIV_ROUND_UP(amount, sdp->sd_jbsize);
        uint64_t *dataptrs = GFS2_EA2DATAPTRS(ea);
        unsigned int x;
        int error = 0;
@@ -628,7 +615,7 @@ static int ea_alloc_blk(struct gfs2_inode *ip, struct buffer_head **bhp)
        block = gfs2_alloc_meta(ip);
 
        *bhp = gfs2_meta_new(ip->i_gl, block);
-       gfs2_trans_add_bh(ip->i_gl, *bhp);
+       gfs2_trans_add_bh(ip->i_gl, *bhp, 1);
        gfs2_metatype_set(*bhp, GFS2_METATYPE_EA, GFS2_FORMAT_EA);
        gfs2_buffer_clear_tail(*bhp, sizeof(struct gfs2_meta_header));
 
@@ -677,7 +664,7 @@ static int ea_write(struct gfs2_inode *ip, struct gfs2_ea_header *ea,
                unsigned int copy;
                unsigned int x;
 
-               ea->ea_num_ptrs = DIV_RU(er->er_data_len, sdp->sd_jbsize);
+               ea->ea_num_ptrs = DIV_ROUND_UP(er->er_data_len, sdp->sd_jbsize);
                for (x = 0; x < ea->ea_num_ptrs; x++) {
                        struct buffer_head *bh;
                        uint64_t block;
@@ -686,7 +673,7 @@ static int ea_write(struct gfs2_inode *ip, struct gfs2_ea_header *ea,
                        block = gfs2_alloc_meta(ip);
 
                        bh = gfs2_meta_new(ip->i_gl, block);
-                       gfs2_trans_add_bh(ip->i_gl, bh);
+                       gfs2_trans_add_bh(ip->i_gl, bh, 1);
                        gfs2_metatype_set(bh, GFS2_METATYPE_ED, GFS2_FORMAT_ED);
 
                        ip->i_di.di_blocks++;
@@ -759,7 +746,7 @@ static int ea_alloc_skeleton(struct gfs2_inode *ip, struct gfs2_ea_request *er,
                        ip->i_di.di_mode = er->er_mode;
                }
                ip->i_di.di_ctime = get_seconds();
-               gfs2_trans_add_bh(ip->i_gl, dibh);
+               gfs2_trans_add_bh(ip->i_gl, dibh, 1);
                gfs2_dinode_out(&ip->i_di, dibh->b_data);
                brelse(dibh);
        }
@@ -811,7 +798,7 @@ static int ea_init(struct gfs2_inode *ip, struct gfs2_ea_request *er)
        unsigned int blks = 1;
 
        if (GFS2_EAREQ_SIZE_STUFFED(er) > jbsize)
-               blks += DIV_RU(er->er_data_len, jbsize);
+               blks += DIV_ROUND_UP(er->er_data_len, jbsize);
 
        return ea_alloc_skeleton(ip, er, blks, ea_init_i, NULL);
 }
@@ -819,7 +806,8 @@ static int ea_init(struct gfs2_inode *ip, struct gfs2_ea_request *er)
 static struct gfs2_ea_header *ea_split_ea(struct gfs2_ea_header *ea)
 {
        uint32_t ea_size = GFS2_EA_SIZE(ea);
-       struct gfs2_ea_header *new = (struct gfs2_ea_header *)((char *)ea + ea_size);
+       struct gfs2_ea_header *new = (struct gfs2_ea_header *)((char *)ea +
+                                    ea_size);
        uint32_t new_size = GFS2_EA_REC_LEN(ea) - ea_size;
        int last = ea->ea_flags & GFS2_EAFLAG_LAST;
 
@@ -839,7 +827,7 @@ static void ea_set_remove_stuffed(struct gfs2_inode *ip,
        struct gfs2_ea_header *prev = el->el_prev;
        uint32_t len;
 
-       gfs2_trans_add_bh(ip->i_gl, el->el_bh);
+       gfs2_trans_add_bh(ip->i_gl, el->el_bh, 1);
 
        if (!prev || !GFS2_EA_IS_STUFFED(ea)) {
                ea->ea_type = GFS2_EATYPE_UNUSED;
@@ -877,7 +865,7 @@ static int ea_set_simple_noalloc(struct gfs2_inode *ip, struct buffer_head *bh,
        if (error)
                return error;
 
-       gfs2_trans_add_bh(ip->i_gl, bh);
+       gfs2_trans_add_bh(ip->i_gl, bh, 1);
 
        if (es->ea_split)
                ea = ea_split_ea(ea);
@@ -897,7 +885,7 @@ static int ea_set_simple_noalloc(struct gfs2_inode *ip, struct buffer_head *bh,
                ip->i_di.di_mode = er->er_mode;
        }
        ip->i_di.di_ctime = get_seconds();
-       gfs2_trans_add_bh(ip->i_gl, dibh);
+       gfs2_trans_add_bh(ip->i_gl, dibh, 1);
        gfs2_dinode_out(&ip->i_di, dibh->b_data);
        brelse(dibh);
  out:
@@ -913,7 +901,7 @@ static int ea_set_simple_alloc(struct gfs2_inode *ip,
        struct gfs2_ea_header *ea = es->es_ea;
        int error;
 
-       gfs2_trans_add_bh(ip->i_gl, es->es_bh);
+       gfs2_trans_add_bh(ip->i_gl, es->es_bh, 1);
 
        if (es->ea_split)
                ea = ea_split_ea(ea);
@@ -962,7 +950,8 @@ static int ea_set_simple(struct gfs2_inode *ip, struct buffer_head *bh,
 
                es->es_bh = bh;
                es->es_ea = ea;
-               blks = 2 + DIV_RU(es->es_er->er_data_len, ip->i_sbd->sd_jbsize);
+               blks = 2 + DIV_ROUND_UP(es->es_er->er_data_len,
+                                       ip->i_sbd->sd_jbsize);
 
                error = ea_alloc_skeleton(ip, es->es_er, blks,
                                          ea_set_simple_alloc, es);
@@ -1007,14 +996,14 @@ static int ea_set_block(struct gfs2_inode *ip, struct gfs2_ea_request *er,
                        goto out;
                }
 
-               gfs2_trans_add_bh(ip->i_gl, indbh);
+               gfs2_trans_add_bh(ip->i_gl, indbh, 1);
        } else {
                uint64_t blk;
 
                blk = gfs2_alloc_meta(ip);
 
                indbh = gfs2_meta_new(ip->i_gl, blk);
-               gfs2_trans_add_bh(ip->i_gl, indbh);
+               gfs2_trans_add_bh(ip->i_gl, indbh, 1);
                gfs2_metatype_set(indbh, GFS2_METATYPE_IN, GFS2_FORMAT_IN);
                gfs2_buffer_clear_tail(indbh, mh_size);
 
@@ -1066,7 +1055,7 @@ static int ea_set_i(struct gfs2_inode *ip, struct gfs2_ea_request *er,
        if (!(ip->i_di.di_flags & GFS2_DIF_EA_INDIRECT))
                blks++;
        if (GFS2_EAREQ_SIZE_STUFFED(er) > ip->i_sbd->sd_jbsize)
-               blks += DIV_RU(er->er_data_len, ip->i_sbd->sd_jbsize);
+               blks += DIV_ROUND_UP(er->er_data_len, ip->i_sbd->sd_jbsize);
 
        return ea_alloc_skeleton(ip, er, blks, ea_set_block, el);
 }
@@ -1163,7 +1152,7 @@ static int ea_remove_stuffed(struct gfs2_inode *ip, struct gfs2_ea_location *el)
        if (error)
                return error;
 
-       gfs2_trans_add_bh(ip->i_gl, el->el_bh);
+       gfs2_trans_add_bh(ip->i_gl, el->el_bh, 1);
 
        if (prev) {
                uint32_t len;
@@ -1179,7 +1168,7 @@ static int ea_remove_stuffed(struct gfs2_inode *ip, struct gfs2_ea_location *el)
        error = gfs2_meta_inode_buffer(ip, &dibh);
        if (!error) {
                ip->i_di.di_ctime = get_seconds();
-               gfs2_trans_add_bh(ip->i_gl, dibh);
+               gfs2_trans_add_bh(ip->i_gl, dibh, 1);
                gfs2_dinode_out(&ip->i_di, dibh->b_data);
                brelse(dibh);
        }       
@@ -1250,7 +1239,7 @@ static int ea_acl_chmod_unstuffed(struct gfs2_inode *ip,
        struct gfs2_sbd *sdp = ip->i_sbd;
        struct buffer_head **bh;
        unsigned int amount = GFS2_EA_DATA_LEN(ea);
-       unsigned int nptrs = DIV_RU(amount, sdp->sd_jbsize);
+       unsigned int nptrs = DIV_ROUND_UP(amount, sdp->sd_jbsize);
        uint64_t *dataptrs = GFS2_EA2DATAPTRS(ea);
        unsigned int x;
        int error;
@@ -1288,7 +1277,7 @@ static int ea_acl_chmod_unstuffed(struct gfs2_inode *ip,
                        goto fail;
                }
 
-               gfs2_trans_add_bh(ip->i_gl, bh[x]);
+               gfs2_trans_add_bh(ip->i_gl, bh[x], 1);
 
                memcpy(bh[x]->b_data + sizeof(struct gfs2_meta_header),
                       data,
@@ -1323,7 +1312,7 @@ int gfs2_ea_acl_chmod(struct gfs2_inode *ip, struct gfs2_ea_location *el,
                if (error)
                        return error;
 
-               gfs2_trans_add_bh(ip->i_gl, el->el_bh);
+               gfs2_trans_add_bh(ip->i_gl, el->el_bh, 1);
                memcpy(GFS2_EA2DATA(el->el_ea),
                       data,
                       GFS2_EA_DATA_LEN(el->el_ea));
@@ -1338,7 +1327,7 @@ int gfs2_ea_acl_chmod(struct gfs2_inode *ip, struct gfs2_ea_location *el,
                error = inode_setattr(ip->i_vnode, attr);
                gfs2_assert_warn(ip->i_sbd, !error);
                gfs2_inode_attr_out(ip);
-               gfs2_trans_add_bh(ip->i_gl, dibh);
+               gfs2_trans_add_bh(ip->i_gl, dibh, 1);
                gfs2_dinode_out(&ip->i_di, dibh->b_data);
                brelse(dibh);
        }
@@ -1402,7 +1391,7 @@ static int ea_dealloc_indirect(struct gfs2_inode *ip)
 
        for (x = 0; x < rlist.rl_rgrps; x++) {
                struct gfs2_rgrpd *rgd;
-               rgd = get_gl2rgd(rlist.rl_ghs[x].gh_gl);
+               rgd = rlist.rl_ghs[x].gh_gl->gl_object;
                rg_blocks += rgd->rd_ri.ri_length;
        }
 
@@ -1416,7 +1405,7 @@ static int ea_dealloc_indirect(struct gfs2_inode *ip)
        if (error)
                goto out_gunlock;
 
-       gfs2_trans_add_bh(ip->i_gl, indbh);
+       gfs2_trans_add_bh(ip->i_gl, indbh, 1);
 
        eablk = (uint64_t *)(indbh->b_data + sizeof(struct gfs2_meta_header));
        bstart = 0;
@@ -1450,7 +1439,7 @@ static int ea_dealloc_indirect(struct gfs2_inode *ip)
 
        error = gfs2_meta_inode_buffer(ip, &dibh);
        if (!error) {
-               gfs2_trans_add_bh(ip->i_gl, dibh);
+               gfs2_trans_add_bh(ip->i_gl, dibh, 1);
                gfs2_dinode_out(&ip->i_di, dibh->b_data);
                brelse(dibh);
        }
@@ -1502,7 +1491,7 @@ static int ea_dealloc_block(struct gfs2_inode *ip)
 
        error = gfs2_meta_inode_buffer(ip, &dibh);
        if (!error) {
-               gfs2_trans_add_bh(ip->i_gl, dibh);
+               gfs2_trans_add_bh(ip->i_gl, dibh, 1);
                gfs2_dinode_out(&ip->i_di, dibh->b_data);
                brelse(dibh);
        }
@@ -1561,60 +1550,3 @@ int gfs2_ea_dealloc(struct gfs2_inode *ip)
        return error;
 }
 
-/**
- * gfs2_get_eattr_meta - return all the eattr blocks of a file
- * @dip: the directory
- * @ub: the structure representing the user buffer to copy to
- *
- * Returns: errno
- */
-
-int gfs2_get_eattr_meta(struct gfs2_inode *ip, struct gfs2_user_buffer *ub)
-{
-       struct buffer_head *bh;
-       int error;
-
-       error = gfs2_meta_read(ip->i_gl, ip->i_di.di_eattr,
-                              DIO_START | DIO_WAIT, &bh);
-       if (error)
-               return error;
-
-       gfs2_add_bh_to_ub(ub, bh);
-
-       if (ip->i_di.di_flags & GFS2_DIF_EA_INDIRECT) {
-               struct buffer_head *eabh;
-               uint64_t *eablk, *end;
-
-               if (gfs2_metatype_check(ip->i_sbd, bh, GFS2_METATYPE_IN)) {
-                       error = -EIO;
-                       goto out;
-               }
-
-               eablk = (uint64_t *)(bh->b_data +
-                                    sizeof(struct gfs2_meta_header));
-               end = eablk + ip->i_sbd->sd_inptrs;
-
-               for (; eablk < end; eablk++) {
-                       uint64_t bn;
-
-                       if (!*eablk)
-                               break;
-                       bn = be64_to_cpu(*eablk);
-
-                       error = gfs2_meta_read(ip->i_gl, bn,
-                                              DIO_START | DIO_WAIT, &eabh);
-                       if (error)
-                               break;
-                       gfs2_add_bh_to_ub(ub, eabh);
-                       brelse(eabh);
-                       if (error)
-                               break;
-               }
-       }
-
- out:
-       brelse(bh);
-
-       return error;
-}
-