4.4BSD snapshot (revision 8.1); add 1993 to copyright
[unix-history] / usr / src / sys / stand.att / bmap.c
CommitLineData
40380a72 1/*-
80409bdc
KB
2 * Copyright (c) 1982, 1988, 1993
3 * The Regents of the University of California. All rights reserved.
40380a72
KB
4 *
5 * %sccs.include.proprietary.c%
6 *
80409bdc 7 * @(#)bmap.c 8.1 (Berkeley) %G%
40380a72
KB
8 */
9
10#include <sys/param.h>
61ef809e 11#include <stand.att/saio.h>
40380a72
KB
12
13#define NBUFS 4
14static char b[NBUFS][MAXBSIZE];
15static daddr_t blknos[NBUFS];
16
17daddr_t
18bmap(io, bn)
19 register struct iob *io;
20 daddr_t bn;
21{
22 register struct dinode *ip;
23 int i, j, sh;
24 daddr_t nb, *bap;
25
26 ip = &io->i_ino;
27 if (bn < 0) {
28 printf("bn negative\n");
29 return ((daddr_t)0);
30 }
31
32 /* The first NDADDR blocks are direct blocks. */
33 if(bn < NDADDR) {
34 nb = ip->di_db[bn];
35 return (nb);
36 }
37
38 /* Determine the number of levels of indirection. */
39 sh = 1;
40 bn -= NDADDR;
41 for (j = NIADDR; j > 0; j--) {
42 sh *= NINDIR(&io->i_fs);
43 if (bn < sh)
44 break;
45 bn -= sh;
46 }
47 if (j == 0) {
de95853c 48 printf("bn ovf %ld\n", bn);
40380a72
KB
49 return ((daddr_t)0);
50 }
51
52 /* Get the first indirect block address. */
53 nb = ip->di_ib[NIADDR - j];
54 if (nb == 0) {
de95853c 55 printf("bn void %ld\n",bn);
40380a72
KB
56 return ((daddr_t)0);
57 }
58
59 /* Get the indirect blocks. */
60 for (; j <= NIADDR; j++) {
61 if (blknos[j] != nb) {
62 io->i_bn = fsbtodb(&io->i_fs, nb) + io->i_boff;
63 io->i_ma = b[j];
64 io->i_cc = io->i_fs.fs_bsize;
65 if (devread(io) != io->i_fs.fs_bsize) {
66 if (io->i_error)
67 errno = io->i_error;
de95853c 68 printf("bn %ld: read error\n", io->i_bn);
40380a72
KB
69 return ((daddr_t)0);
70 }
71 blknos[j] = nb;
72 }
73 bap = (daddr_t *)b[j];
74 sh /= NINDIR(&io->i_fs);
75 i = (bn / sh) % NINDIR(&io->i_fs);
76 nb = bap[i];
77 if(nb == 0) {
de95853c 78 printf("bn void %ld\n",bn);
40380a72
KB
79 return ((daddr_t)0);
80 }
81 }
82 return (nb);
83}