1*b2441318SGreg Kroah-Hartman // SPDX-License-Identifier: GPL-2.0
21da177e4SLinus Torvalds /*
31da177e4SLinus Torvalds * linux/fs/hpfs/ea.c
41da177e4SLinus Torvalds *
51da177e4SLinus Torvalds * Mikulas Patocka (mikulas@artax.karlin.mff.cuni.cz), 1998-1999
61da177e4SLinus Torvalds *
71da177e4SLinus Torvalds * handling extended attributes
81da177e4SLinus Torvalds */
91da177e4SLinus Torvalds
101da177e4SLinus Torvalds #include "hpfs_fn.h"
111da177e4SLinus Torvalds
121da177e4SLinus Torvalds /* Remove external extended attributes. ano specifies whether a is a
131da177e4SLinus Torvalds direct sector where eas starts or an anode */
141da177e4SLinus Torvalds
hpfs_ea_ext_remove(struct super_block * s,secno a,int ano,unsigned len)151da177e4SLinus Torvalds void hpfs_ea_ext_remove(struct super_block *s, secno a, int ano, unsigned len)
161da177e4SLinus Torvalds {
171da177e4SLinus Torvalds unsigned pos = 0;
181da177e4SLinus Torvalds while (pos < len) {
191da177e4SLinus Torvalds char ex[4 + 255 + 1 + 8];
201da177e4SLinus Torvalds struct extended_attribute *ea = (struct extended_attribute *)ex;
211da177e4SLinus Torvalds if (pos + 4 > len) {
221da177e4SLinus Torvalds hpfs_error(s, "EAs don't end correctly, %s %08x, len %08x",
231da177e4SLinus Torvalds ano ? "anode" : "sectors", a, len);
241da177e4SLinus Torvalds return;
251da177e4SLinus Torvalds }
261da177e4SLinus Torvalds if (hpfs_ea_read(s, a, ano, pos, 4, ex)) return;
274085e155SAl Viro if (ea_indirect(ea)) {
28d0969d19SMikulas Patocka if (ea_valuelen(ea) != 8) {
294085e155SAl Viro hpfs_error(s, "ea_indirect(ea) set while ea->valuelen!=8, %s %08x, pos %08x",
301da177e4SLinus Torvalds ano ? "anode" : "sectors", a, pos);
311da177e4SLinus Torvalds return;
321da177e4SLinus Torvalds }
331da177e4SLinus Torvalds if (hpfs_ea_read(s, a, ano, pos + 4, ea->namelen + 9, ex+4))
341da177e4SLinus Torvalds return;
354085e155SAl Viro hpfs_ea_remove(s, ea_sec(ea), ea_in_anode(ea), ea_len(ea));
361da177e4SLinus Torvalds }
37d0969d19SMikulas Patocka pos += ea->namelen + ea_valuelen(ea) + 5;
381da177e4SLinus Torvalds }
391da177e4SLinus Torvalds if (!ano) hpfs_free_sectors(s, a, (len+511) >> 9);
401da177e4SLinus Torvalds else {
411da177e4SLinus Torvalds struct buffer_head *bh;
421da177e4SLinus Torvalds struct anode *anode;
431da177e4SLinus Torvalds if ((anode = hpfs_map_anode(s, a, &bh))) {
441da177e4SLinus Torvalds hpfs_remove_btree(s, &anode->btree);
451da177e4SLinus Torvalds brelse(bh);
461da177e4SLinus Torvalds hpfs_free_sectors(s, a, 1);
471da177e4SLinus Torvalds }
481da177e4SLinus Torvalds }
491da177e4SLinus Torvalds }
501da177e4SLinus Torvalds
get_indirect_ea(struct super_block * s,int ano,secno a,int size)511da177e4SLinus Torvalds static char *get_indirect_ea(struct super_block *s, int ano, secno a, int size)
521da177e4SLinus Torvalds {
531da177e4SLinus Torvalds char *ret;
541da177e4SLinus Torvalds if (!(ret = kmalloc(size + 1, GFP_NOFS))) {
55a19189e5SFabian Frederick pr_err("out of memory for EA\n");
561da177e4SLinus Torvalds return NULL;
571da177e4SLinus Torvalds }
581da177e4SLinus Torvalds if (hpfs_ea_read(s, a, ano, 0, size, ret)) {
591da177e4SLinus Torvalds kfree(ret);
601da177e4SLinus Torvalds return NULL;
611da177e4SLinus Torvalds }
621da177e4SLinus Torvalds ret[size] = 0;
631da177e4SLinus Torvalds return ret;
641da177e4SLinus Torvalds }
651da177e4SLinus Torvalds
set_indirect_ea(struct super_block * s,int ano,secno a,const char * data,int size)667e7742eeSAl Viro static void set_indirect_ea(struct super_block *s, int ano, secno a,
677e7742eeSAl Viro const char *data, int size)
681da177e4SLinus Torvalds {
691da177e4SLinus Torvalds hpfs_ea_write(s, a, ano, 0, size, data);
701da177e4SLinus Torvalds }
711da177e4SLinus Torvalds
721da177e4SLinus Torvalds /* Read an extended attribute named 'key' into the provided buffer */
731da177e4SLinus Torvalds
hpfs_read_ea(struct super_block * s,struct fnode * fnode,char * key,char * buf,int size)741da177e4SLinus Torvalds int hpfs_read_ea(struct super_block *s, struct fnode *fnode, char *key,
751da177e4SLinus Torvalds char *buf, int size)
761da177e4SLinus Torvalds {
771da177e4SLinus Torvalds unsigned pos;
781da177e4SLinus Torvalds int ano, len;
791da177e4SLinus Torvalds secno a;
80c3514817SMikulas Patocka char ex[4 + 255 + 1 + 8];
811da177e4SLinus Torvalds struct extended_attribute *ea;
821da177e4SLinus Torvalds struct extended_attribute *ea_end = fnode_end_ea(fnode);
831da177e4SLinus Torvalds for (ea = fnode_ea(fnode); ea < ea_end; ea = next_ea(ea))
841da177e4SLinus Torvalds if (!strcmp(ea->name, key)) {
854085e155SAl Viro if (ea_indirect(ea))
861da177e4SLinus Torvalds goto indirect;
87d0969d19SMikulas Patocka if (ea_valuelen(ea) >= size)
881da177e4SLinus Torvalds return -EINVAL;
89d0969d19SMikulas Patocka memcpy(buf, ea_data(ea), ea_valuelen(ea));
90d0969d19SMikulas Patocka buf[ea_valuelen(ea)] = 0;
911da177e4SLinus Torvalds return 0;
921da177e4SLinus Torvalds }
930b69760bSMikulas Patocka a = le32_to_cpu(fnode->ea_secno);
940b69760bSMikulas Patocka len = le32_to_cpu(fnode->ea_size_l);
95c4c99543SAl Viro ano = fnode_in_anode(fnode);
961da177e4SLinus Torvalds pos = 0;
971da177e4SLinus Torvalds while (pos < len) {
981da177e4SLinus Torvalds ea = (struct extended_attribute *)ex;
991da177e4SLinus Torvalds if (pos + 4 > len) {
1001da177e4SLinus Torvalds hpfs_error(s, "EAs don't end correctly, %s %08x, len %08x",
1011da177e4SLinus Torvalds ano ? "anode" : "sectors", a, len);
1021da177e4SLinus Torvalds return -EIO;
1031da177e4SLinus Torvalds }
1041da177e4SLinus Torvalds if (hpfs_ea_read(s, a, ano, pos, 4, ex)) return -EIO;
1054085e155SAl Viro if (hpfs_ea_read(s, a, ano, pos + 4, ea->namelen + 1 + (ea_indirect(ea) ? 8 : 0), ex + 4))
1061da177e4SLinus Torvalds return -EIO;
1071da177e4SLinus Torvalds if (!strcmp(ea->name, key)) {
1084085e155SAl Viro if (ea_indirect(ea))
1091da177e4SLinus Torvalds goto indirect;
110d0969d19SMikulas Patocka if (ea_valuelen(ea) >= size)
1111da177e4SLinus Torvalds return -EINVAL;
112d0969d19SMikulas Patocka if (hpfs_ea_read(s, a, ano, pos + 4 + ea->namelen + 1, ea_valuelen(ea), buf))
1131da177e4SLinus Torvalds return -EIO;
114d0969d19SMikulas Patocka buf[ea_valuelen(ea)] = 0;
1151da177e4SLinus Torvalds return 0;
1161da177e4SLinus Torvalds }
117d0969d19SMikulas Patocka pos += ea->namelen + ea_valuelen(ea) + 5;
1181da177e4SLinus Torvalds }
1191da177e4SLinus Torvalds return -ENOENT;
1201da177e4SLinus Torvalds indirect:
1211da177e4SLinus Torvalds if (ea_len(ea) >= size)
1221da177e4SLinus Torvalds return -EINVAL;
1234085e155SAl Viro if (hpfs_ea_read(s, ea_sec(ea), ea_in_anode(ea), 0, ea_len(ea), buf))
1241da177e4SLinus Torvalds return -EIO;
1251da177e4SLinus Torvalds buf[ea_len(ea)] = 0;
1261da177e4SLinus Torvalds return 0;
1271da177e4SLinus Torvalds }
1281da177e4SLinus Torvalds
1291da177e4SLinus Torvalds /* Read an extended attribute named 'key' */
hpfs_get_ea(struct super_block * s,struct fnode * fnode,char * key,int * size)1301da177e4SLinus Torvalds char *hpfs_get_ea(struct super_block *s, struct fnode *fnode, char *key, int *size)
1311da177e4SLinus Torvalds {
1321da177e4SLinus Torvalds char *ret;
1331da177e4SLinus Torvalds unsigned pos;
1341da177e4SLinus Torvalds int ano, len;
1351da177e4SLinus Torvalds secno a;
1361da177e4SLinus Torvalds struct extended_attribute *ea;
1371da177e4SLinus Torvalds struct extended_attribute *ea_end = fnode_end_ea(fnode);
1381da177e4SLinus Torvalds for (ea = fnode_ea(fnode); ea < ea_end; ea = next_ea(ea))
1391da177e4SLinus Torvalds if (!strcmp(ea->name, key)) {
1404085e155SAl Viro if (ea_indirect(ea))
1414085e155SAl Viro return get_indirect_ea(s, ea_in_anode(ea), ea_sec(ea), *size = ea_len(ea));
142d0969d19SMikulas Patocka if (!(ret = kmalloc((*size = ea_valuelen(ea)) + 1, GFP_NOFS))) {
143a19189e5SFabian Frederick pr_err("out of memory for EA\n");
1441da177e4SLinus Torvalds return NULL;
1451da177e4SLinus Torvalds }
146d0969d19SMikulas Patocka memcpy(ret, ea_data(ea), ea_valuelen(ea));
147d0969d19SMikulas Patocka ret[ea_valuelen(ea)] = 0;
1481da177e4SLinus Torvalds return ret;
1491da177e4SLinus Torvalds }
1500b69760bSMikulas Patocka a = le32_to_cpu(fnode->ea_secno);
1510b69760bSMikulas Patocka len = le32_to_cpu(fnode->ea_size_l);
152c4c99543SAl Viro ano = fnode_in_anode(fnode);
1531da177e4SLinus Torvalds pos = 0;
1541da177e4SLinus Torvalds while (pos < len) {
1551da177e4SLinus Torvalds char ex[4 + 255 + 1 + 8];
1561da177e4SLinus Torvalds ea = (struct extended_attribute *)ex;
1571da177e4SLinus Torvalds if (pos + 4 > len) {
1581da177e4SLinus Torvalds hpfs_error(s, "EAs don't end correctly, %s %08x, len %08x",
1591da177e4SLinus Torvalds ano ? "anode" : "sectors", a, len);
1601da177e4SLinus Torvalds return NULL;
1611da177e4SLinus Torvalds }
1621da177e4SLinus Torvalds if (hpfs_ea_read(s, a, ano, pos, 4, ex)) return NULL;
1634085e155SAl Viro if (hpfs_ea_read(s, a, ano, pos + 4, ea->namelen + 1 + (ea_indirect(ea) ? 8 : 0), ex + 4))
1641da177e4SLinus Torvalds return NULL;
1651da177e4SLinus Torvalds if (!strcmp(ea->name, key)) {
1664085e155SAl Viro if (ea_indirect(ea))
1674085e155SAl Viro return get_indirect_ea(s, ea_in_anode(ea), ea_sec(ea), *size = ea_len(ea));
168d0969d19SMikulas Patocka if (!(ret = kmalloc((*size = ea_valuelen(ea)) + 1, GFP_NOFS))) {
169a19189e5SFabian Frederick pr_err("out of memory for EA\n");
1701da177e4SLinus Torvalds return NULL;
1711da177e4SLinus Torvalds }
172d0969d19SMikulas Patocka if (hpfs_ea_read(s, a, ano, pos + 4 + ea->namelen + 1, ea_valuelen(ea), ret)) {
1731da177e4SLinus Torvalds kfree(ret);
1741da177e4SLinus Torvalds return NULL;
1751da177e4SLinus Torvalds }
176d0969d19SMikulas Patocka ret[ea_valuelen(ea)] = 0;
1771da177e4SLinus Torvalds return ret;
1781da177e4SLinus Torvalds }
179d0969d19SMikulas Patocka pos += ea->namelen + ea_valuelen(ea) + 5;
1801da177e4SLinus Torvalds }
1811da177e4SLinus Torvalds return NULL;
1821da177e4SLinus Torvalds }
1831da177e4SLinus Torvalds
1841da177e4SLinus Torvalds /*
1851da177e4SLinus Torvalds * Update or create extended attribute 'key' with value 'data'. Note that
1861da177e4SLinus Torvalds * when this ea exists, it MUST have the same size as size of data.
1871da177e4SLinus Torvalds * This driver can't change sizes of eas ('cause I just don't need it).
1881da177e4SLinus Torvalds */
1891da177e4SLinus Torvalds
hpfs_set_ea(struct inode * inode,struct fnode * fnode,const char * key,const char * data,int size)1907e7742eeSAl Viro void hpfs_set_ea(struct inode *inode, struct fnode *fnode, const char *key,
1917e7742eeSAl Viro const char *data, int size)
1921da177e4SLinus Torvalds {
1931da177e4SLinus Torvalds fnode_secno fno = inode->i_ino;
1941da177e4SLinus Torvalds struct super_block *s = inode->i_sb;
1951da177e4SLinus Torvalds unsigned pos;
1961da177e4SLinus Torvalds int ano, len;
1971da177e4SLinus Torvalds secno a;
1981da177e4SLinus Torvalds unsigned char h[4];
1991da177e4SLinus Torvalds struct extended_attribute *ea;
2001da177e4SLinus Torvalds struct extended_attribute *ea_end = fnode_end_ea(fnode);
2011da177e4SLinus Torvalds for (ea = fnode_ea(fnode); ea < ea_end; ea = next_ea(ea))
2021da177e4SLinus Torvalds if (!strcmp(ea->name, key)) {
2034085e155SAl Viro if (ea_indirect(ea)) {
2041da177e4SLinus Torvalds if (ea_len(ea) == size)
2054085e155SAl Viro set_indirect_ea(s, ea_in_anode(ea), ea_sec(ea), data, size);
206d0969d19SMikulas Patocka } else if (ea_valuelen(ea) == size) {
2071da177e4SLinus Torvalds memcpy(ea_data(ea), data, size);
2081da177e4SLinus Torvalds }
2091da177e4SLinus Torvalds return;
2101da177e4SLinus Torvalds }
2110b69760bSMikulas Patocka a = le32_to_cpu(fnode->ea_secno);
2120b69760bSMikulas Patocka len = le32_to_cpu(fnode->ea_size_l);
213c4c99543SAl Viro ano = fnode_in_anode(fnode);
2141da177e4SLinus Torvalds pos = 0;
2151da177e4SLinus Torvalds while (pos < len) {
2161da177e4SLinus Torvalds char ex[4 + 255 + 1 + 8];
2171da177e4SLinus Torvalds ea = (struct extended_attribute *)ex;
2181da177e4SLinus Torvalds if (pos + 4 > len) {
2191da177e4SLinus Torvalds hpfs_error(s, "EAs don't end correctly, %s %08x, len %08x",
2201da177e4SLinus Torvalds ano ? "anode" : "sectors", a, len);
2211da177e4SLinus Torvalds return;
2221da177e4SLinus Torvalds }
2231da177e4SLinus Torvalds if (hpfs_ea_read(s, a, ano, pos, 4, ex)) return;
2244085e155SAl Viro if (hpfs_ea_read(s, a, ano, pos + 4, ea->namelen + 1 + (ea_indirect(ea) ? 8 : 0), ex + 4))
2251da177e4SLinus Torvalds return;
2261da177e4SLinus Torvalds if (!strcmp(ea->name, key)) {
2274085e155SAl Viro if (ea_indirect(ea)) {
2281da177e4SLinus Torvalds if (ea_len(ea) == size)
2294085e155SAl Viro set_indirect_ea(s, ea_in_anode(ea), ea_sec(ea), data, size);
2301da177e4SLinus Torvalds }
2311da177e4SLinus Torvalds else {
232d0969d19SMikulas Patocka if (ea_valuelen(ea) == size)
2331da177e4SLinus Torvalds hpfs_ea_write(s, a, ano, pos + 4 + ea->namelen + 1, size, data);
2341da177e4SLinus Torvalds }
2351da177e4SLinus Torvalds return;
2361da177e4SLinus Torvalds }
237d0969d19SMikulas Patocka pos += ea->namelen + ea_valuelen(ea) + 5;
2381da177e4SLinus Torvalds }
2390b69760bSMikulas Patocka if (!le16_to_cpu(fnode->ea_offs)) {
2400b69760bSMikulas Patocka /*if (le16_to_cpu(fnode->ea_size_s)) {
2411da177e4SLinus Torvalds hpfs_error(s, "fnode %08x: ea_size_s == %03x, ea_offs == 0",
2420b69760bSMikulas Patocka inode->i_ino, le16_to_cpu(fnode->ea_size_s));
2431da177e4SLinus Torvalds return;
2441da177e4SLinus Torvalds }*/
2450b69760bSMikulas Patocka fnode->ea_offs = cpu_to_le16(0xc4);
2461da177e4SLinus Torvalds }
2470b69760bSMikulas Patocka if (le16_to_cpu(fnode->ea_offs) < 0xc4 || le16_to_cpu(fnode->ea_offs) + le16_to_cpu(fnode->acl_size_s) + le16_to_cpu(fnode->ea_size_s) > 0x200) {
24818debbbcSRandy Dunlap hpfs_error(s, "fnode %08lx: ea_offs == %03x, ea_size_s == %03x",
24918debbbcSRandy Dunlap (unsigned long)inode->i_ino,
250de5e2b36SAl Viro le16_to_cpu(fnode->ea_offs), le16_to_cpu(fnode->ea_size_s));
2511da177e4SLinus Torvalds return;
2521da177e4SLinus Torvalds }
2530b69760bSMikulas Patocka if ((le16_to_cpu(fnode->ea_size_s) || !le32_to_cpu(fnode->ea_size_l)) &&
2540b69760bSMikulas Patocka le16_to_cpu(fnode->ea_offs) + le16_to_cpu(fnode->acl_size_s) + le16_to_cpu(fnode->ea_size_s) + strlen(key) + size + 5 <= 0x200) {
2551da177e4SLinus Torvalds ea = fnode_end_ea(fnode);
2561da177e4SLinus Torvalds *(char *)ea = 0;
2571da177e4SLinus Torvalds ea->namelen = strlen(key);
258d0969d19SMikulas Patocka ea->valuelen_lo = size;
259d0969d19SMikulas Patocka ea->valuelen_hi = size >> 8;
2601da177e4SLinus Torvalds strcpy(ea->name, key);
2611da177e4SLinus Torvalds memcpy(ea_data(ea), data, size);
2620b69760bSMikulas Patocka fnode->ea_size_s = cpu_to_le16(le16_to_cpu(fnode->ea_size_s) + strlen(key) + size + 5);
2631da177e4SLinus Torvalds goto ret;
2641da177e4SLinus Torvalds }
2651da177e4SLinus Torvalds /* Most the code here is 99.9993422% unused. I hope there are no bugs.
2661da177e4SLinus Torvalds But what .. HPFS.IFS has also bugs in ea management. */
2670b69760bSMikulas Patocka if (le16_to_cpu(fnode->ea_size_s) && !le32_to_cpu(fnode->ea_size_l)) {
2681da177e4SLinus Torvalds secno n;
2691da177e4SLinus Torvalds struct buffer_head *bh;
2701da177e4SLinus Torvalds char *data;
2717d23ce36SMikulas Patocka if (!(n = hpfs_alloc_sector(s, fno, 1, 0))) return;
2721da177e4SLinus Torvalds if (!(data = hpfs_get_sector(s, n, &bh))) {
2731da177e4SLinus Torvalds hpfs_free_sectors(s, n, 1);
2741da177e4SLinus Torvalds return;
2751da177e4SLinus Torvalds }
2760b69760bSMikulas Patocka memcpy(data, fnode_ea(fnode), le16_to_cpu(fnode->ea_size_s));
2770b69760bSMikulas Patocka fnode->ea_size_l = cpu_to_le32(le16_to_cpu(fnode->ea_size_s));
2780b69760bSMikulas Patocka fnode->ea_size_s = cpu_to_le16(0);
2790b69760bSMikulas Patocka fnode->ea_secno = cpu_to_le32(n);
280c4c99543SAl Viro fnode->flags &= ~FNODE_anode;
2811da177e4SLinus Torvalds mark_buffer_dirty(bh);
2821da177e4SLinus Torvalds brelse(bh);
2831da177e4SLinus Torvalds }
2840b69760bSMikulas Patocka pos = le32_to_cpu(fnode->ea_size_l) + 5 + strlen(key) + size;
2850b69760bSMikulas Patocka len = (le32_to_cpu(fnode->ea_size_l) + 511) >> 9;
2861da177e4SLinus Torvalds if (pos >= 30000) goto bail;
2871da177e4SLinus Torvalds while (((pos + 511) >> 9) > len) {
2881da177e4SLinus Torvalds if (!len) {
2890b69760bSMikulas Patocka secno q = hpfs_alloc_sector(s, fno, 1, 0);
2900b69760bSMikulas Patocka if (!q) goto bail;
2910b69760bSMikulas Patocka fnode->ea_secno = cpu_to_le32(q);
292c4c99543SAl Viro fnode->flags &= ~FNODE_anode;
2931da177e4SLinus Torvalds len++;
294c4c99543SAl Viro } else if (!fnode_in_anode(fnode)) {
2950b69760bSMikulas Patocka if (hpfs_alloc_if_possible(s, le32_to_cpu(fnode->ea_secno) + len)) {
2961da177e4SLinus Torvalds len++;
2971da177e4SLinus Torvalds } else {
2981da177e4SLinus Torvalds /* Aargh... don't know how to create ea anodes :-( */
2991da177e4SLinus Torvalds /*struct buffer_head *bh;
3001da177e4SLinus Torvalds struct anode *anode;
3011da177e4SLinus Torvalds anode_secno a_s;
3021da177e4SLinus Torvalds if (!(anode = hpfs_alloc_anode(s, fno, &a_s, &bh)))
3031da177e4SLinus Torvalds goto bail;
3040b69760bSMikulas Patocka anode->up = cpu_to_le32(fno);
3051da177e4SLinus Torvalds anode->btree.fnode_parent = 1;
3061da177e4SLinus Torvalds anode->btree.n_free_nodes--;
3071da177e4SLinus Torvalds anode->btree.n_used_nodes++;
3080b69760bSMikulas Patocka anode->btree.first_free = cpu_to_le16(le16_to_cpu(anode->btree.first_free) + 12);
3090b69760bSMikulas Patocka anode->u.external[0].disk_secno = cpu_to_le32(le32_to_cpu(fnode->ea_secno));
3100b69760bSMikulas Patocka anode->u.external[0].file_secno = cpu_to_le32(0);
3110b69760bSMikulas Patocka anode->u.external[0].length = cpu_to_le32(len);
3121da177e4SLinus Torvalds mark_buffer_dirty(bh);
3131da177e4SLinus Torvalds brelse(bh);
314c4c99543SAl Viro fnode->flags |= FNODE_anode;
3150b69760bSMikulas Patocka fnode->ea_secno = cpu_to_le32(a_s);*/
3161da177e4SLinus Torvalds secno new_sec;
3171da177e4SLinus Torvalds int i;
3187d23ce36SMikulas Patocka if (!(new_sec = hpfs_alloc_sector(s, fno, 1, 1 - ((pos + 511) >> 9))))
3191da177e4SLinus Torvalds goto bail;
3201da177e4SLinus Torvalds for (i = 0; i < len; i++) {
3211da177e4SLinus Torvalds struct buffer_head *bh1, *bh2;
3221da177e4SLinus Torvalds void *b1, *b2;
3230b69760bSMikulas Patocka if (!(b1 = hpfs_map_sector(s, le32_to_cpu(fnode->ea_secno) + i, &bh1, len - i - 1))) {
3241da177e4SLinus Torvalds hpfs_free_sectors(s, new_sec, (pos + 511) >> 9);
3251da177e4SLinus Torvalds goto bail;
3261da177e4SLinus Torvalds }
3271da177e4SLinus Torvalds if (!(b2 = hpfs_get_sector(s, new_sec + i, &bh2))) {
3281da177e4SLinus Torvalds brelse(bh1);
3291da177e4SLinus Torvalds hpfs_free_sectors(s, new_sec, (pos + 511) >> 9);
3301da177e4SLinus Torvalds goto bail;
3311da177e4SLinus Torvalds }
3321da177e4SLinus Torvalds memcpy(b2, b1, 512);
3331da177e4SLinus Torvalds brelse(bh1);
3341da177e4SLinus Torvalds mark_buffer_dirty(bh2);
3351da177e4SLinus Torvalds brelse(bh2);
3361da177e4SLinus Torvalds }
3370b69760bSMikulas Patocka hpfs_free_sectors(s, le32_to_cpu(fnode->ea_secno), len);
3380b69760bSMikulas Patocka fnode->ea_secno = cpu_to_le32(new_sec);
3391da177e4SLinus Torvalds len = (pos + 511) >> 9;
3401da177e4SLinus Torvalds }
3411da177e4SLinus Torvalds }
342c4c99543SAl Viro if (fnode_in_anode(fnode)) {
3430b69760bSMikulas Patocka if (hpfs_add_sector_to_btree(s, le32_to_cpu(fnode->ea_secno),
3441da177e4SLinus Torvalds 0, len) != -1) {
3451da177e4SLinus Torvalds len++;
3461da177e4SLinus Torvalds } else {
3471da177e4SLinus Torvalds goto bail;
3481da177e4SLinus Torvalds }
3491da177e4SLinus Torvalds }
3501da177e4SLinus Torvalds }
3511da177e4SLinus Torvalds h[0] = 0;
3521da177e4SLinus Torvalds h[1] = strlen(key);
3531da177e4SLinus Torvalds h[2] = size & 0xff;
3541da177e4SLinus Torvalds h[3] = size >> 8;
355c4c99543SAl Viro if (hpfs_ea_write(s, le32_to_cpu(fnode->ea_secno), fnode_in_anode(fnode), le32_to_cpu(fnode->ea_size_l), 4, h)) goto bail;
356c4c99543SAl Viro if (hpfs_ea_write(s, le32_to_cpu(fnode->ea_secno), fnode_in_anode(fnode), le32_to_cpu(fnode->ea_size_l) + 4, h[1] + 1, key)) goto bail;
357c4c99543SAl Viro if (hpfs_ea_write(s, le32_to_cpu(fnode->ea_secno), fnode_in_anode(fnode), le32_to_cpu(fnode->ea_size_l) + 5 + h[1], size, data)) goto bail;
3580b69760bSMikulas Patocka fnode->ea_size_l = cpu_to_le32(pos);
3591da177e4SLinus Torvalds ret:
3601da177e4SLinus Torvalds hpfs_i(inode)->i_ea_size += 5 + strlen(key) + size;
3611da177e4SLinus Torvalds return;
3621da177e4SLinus Torvalds bail:
3630b69760bSMikulas Patocka if (le32_to_cpu(fnode->ea_secno))
364c4c99543SAl Viro if (fnode_in_anode(fnode)) hpfs_truncate_btree(s, le32_to_cpu(fnode->ea_secno), 1, (le32_to_cpu(fnode->ea_size_l) + 511) >> 9);
3650b69760bSMikulas Patocka else hpfs_free_sectors(s, le32_to_cpu(fnode->ea_secno) + ((le32_to_cpu(fnode->ea_size_l) + 511) >> 9), len - ((le32_to_cpu(fnode->ea_size_l) + 511) >> 9));
3660b69760bSMikulas Patocka else fnode->ea_secno = fnode->ea_size_l = cpu_to_le32(0);
3671da177e4SLinus Torvalds }
3681da177e4SLinus Torvalds
369