2 * Copyright (C) 2011+ Evgeniy Polyakov <zbr@ioremap.net>
5 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
9 static int pohmelfs_stat_init(struct pohmelfs_trans
*t
)
11 struct pohmelfs_wait
*wait
= t
->priv
;
13 atomic_long_inc(&wait
->count
);
14 pohmelfs_wait_get(wait
);
18 static void pohmelfs_stat_destroy(struct pohmelfs_trans
*t
)
20 struct pohmelfs_wait
*wait
= t
->priv
;
22 atomic_long_dec(&wait
->count
);
24 pohmelfs_wait_put(wait
);
27 static int pohmelfs_stat_complete(struct pohmelfs_trans
*t
, struct pohmelfs_state
*recv
)
29 struct pohmelfs_wait
*wait
= t
->priv
;
30 struct dnet_cmd
*cmd
= &recv
->cmd
;
31 struct dnet_attr
*attr
;
32 int err
= cmd
->status
;
37 if (cmd
->size
!= sizeof(struct dnet_attr
) + sizeof(struct dnet_stat
)) {
44 if ((cmd
->flags
& DNET_FLAGS_MORE
) && (attr
->cmd
== DNET_CMD_STAT
) && (attr
->size
== sizeof(struct dnet_stat
))) {
45 struct dnet_stat
*stat
;
47 stat
= t
->recv_data
+ sizeof(struct dnet_attr
);
48 dnet_convert_stat(stat
);
50 recv
->bsize
= stat
->bsize
;
51 recv
->frsize
= stat
->frsize
;
52 recv
->blocks
= stat
->blocks
;
53 recv
->bfree
= stat
->bfree
;
54 recv
->bavail
= stat
->bavail
;
56 pr_debug("%s: total: %llu, avail: %llu\n",
57 pohmelfs_dump_id(cmd
->id
.id
),
58 (unsigned long long)(stat
->frsize
* stat
->blocks
/ 1024 / 1024),
59 (unsigned long long)(stat
->bavail
* stat
->bsize
/ 1024 / 1024));
64 wait
->condition
= err
;
72 int pohmelfs_stat(struct pohmelfs_sb
*psb
, int sync
)
74 struct pohmelfs_state
**states
, *st
;
75 struct pohmelfs_wait
*wait
;
76 struct pohmelfs_io
*pio
;
80 wait
= pohmelfs_wait_alloc(psb
->root
);
86 pio
= kmem_cache_zalloc(pohmelfs_io_cache
, GFP_NOIO
);
92 err
= pohmelfs_grab_states(psb
, &states
);
94 goto err_out_free_pio
;
97 /* we use state pointer, but do not know correct ID, so use DIRECT flag here to forbid request forwarding */
98 pio
->cflags
= DNET_FLAGS_NEED_ACK
| DNET_FLAGS_NOLOCK
| DNET_FLAGS_DIRECT
;
99 pio
->cmd
= DNET_CMD_STAT
;
101 pio
->cb
.init
= pohmelfs_stat_init
;
102 pio
->cb
.destroy
= pohmelfs_stat_destroy
;
103 pio
->cb
.complete
= pohmelfs_stat_complete
;
106 for (i
= 0; i
< num
; ++i
) {
109 pio
->group_id
= st
->group_id
;
110 pio
->id
= &psb
->root
->id
;
112 err
= pohmelfs_send_buf_single(pio
, st
);
113 pohmelfs_state_put(st
);
119 ret
= wait_event_interruptible_timeout(wait
->wq
,
120 atomic_long_read(&wait
->count
) != 0,
121 msecs_to_jiffies(psb
->read_wait_timeout
));
129 if (wait
->condition
< 0)
130 err
= wait
->condition
;
136 kmem_cache_free(pohmelfs_io_cache
, pio
);
138 pohmelfs_wait_put(wait
);