aoe  87
About: AoE (ATA over Ethernet) Protocol Driver (Linux kernel 4.8.x and greater are not supported).
  Fossies Dox: aoe-87.tar.gz  ("inofficial" and yet experimental doxygen-generated source code documentation)  

aoedbg.c
Go to the documentation of this file.
1 #include <linux/skbuff.h>
2 #include <linux/hdreg.h>
3 #include <linux/mempool.h>
4 #include <linux/debugfs.h>
5 #include <linux/relay.h>
6 #include "aoe.h"
7 
8 #define SUBBUF_SIZE 262144
9 #define N_SUBBUFS 8
10 
11 /* aoe module channel for ad hoc messages */
12 static struct rchan *chan;
13 
14 static struct timeval start;
15 
16 /* per-aoedev debugging support */
17 struct ddbg {
18  struct rchan *rttchan;
19  atomic_t rttseq;
20 };
21 
22 static char buf[PAGE_SIZE];
23 static DEFINE_SPINLOCK(buflock);
24 
25 /* required callbacks for using debugfs as host fs for relay */
26 static struct dentry *
27 cfile(const char *filename,
28  struct dentry *parent,
29  umode_t mode,
30  struct rchan_buf *buf,
31  int *is_global)
32 {
33  return debugfs_create_file(filename, mode, parent, buf,
34  &relay_file_operations);
35 }
36 static int
37 rfile(struct dentry *dentry)
38 {
39  debugfs_remove(dentry);
40 
41  return 0;
42 }
43 static int
44 subbuf_start(struct rchan_buf *buf,
45  void *subbuf,
46  void *prev_subbuf,
47  size_t prev_padding)
48 {
49  return 1; /* overwrite mode */
50 }
51 static struct rchan_callbacks cb = {
52  .subbuf_start = subbuf_start,
53  .create_buf_file = cfile,
54  .remove_buf_file = rfile,
55 };
56 
57 /* Only call xrelay_open from code that can sleep. */
58 static struct rchan *
59 xrelay_open(const char *base_fnam,
60  struct dentry *parent,
61  size_t subbuf_size,
62  size_t n_subbufs)
63 {
64  struct rchan *c;
65 
66  c = relay_open(base_fnam, parent, subbuf_size, n_subbufs, &cb, NULL);
67 
68  if (!c)
69  printk(KERN_ERR
70  "aoe: could not create relay channel %s\n",
71  base_fnam);
72  else
73  printk(KERN_INFO
74  "aoe: relay channel %s ready\n", base_fnam);
75 
76  return c;
77 }
78 
79 void __init
81 {
82  enum {
83  AOE_CHAN_SUBBUF_SIZE = 1024 * 64,
84  AOE_CHAN_N_SUBBUFS = 4,
85  };
86 
87  if (!AOEDBG_ACTIVE)
88  return;
89 
90  chan = xrelay_open("aoe", NULL,
91  AOE_CHAN_SUBBUF_SIZE, AOE_CHAN_N_SUBBUFS);
92 
93  do_gettimeofday(&start);
94 }
95 
96 static void
97 aoedbg_write(const void *data, size_t length)
98 {
99  if (!chan)
100  return;
101 
102  relay_write(chan, data, length);
103 }
104 
105 /* formatted printing on the aoe-module generic channel */
106 void
107 aoedbg_print(char *fmt, ...)
108 {
109  va_list va;
110  unsigned long flags;
111  int n;
112 
113  if (!chan)
114  return;
115 
116  va_start(va, fmt);
117  spin_lock_irqsave(&buflock, flags);
118  n = vsnprintf(buf, sizeof buf - 1, fmt, va);
119  spin_unlock_irqrestore(&buflock, flags);
120  aoedbg_write(buf, n);
121 }
122 
123 static int
124 rttstart(struct aoedev *d)
125 {
126  struct ddbg *dbg;
127  struct rchan *c;
128  char name[32] = { 0, };
129 
130  snprintf(name, sizeof name - 1,
131  "aoe-e%ld.%d-rtts",
132  d->aoemajor, d->aoeminor);
133  c = xrelay_open(name, NULL, SUBBUF_SIZE, N_SUBBUFS);
134  if (!c)
135  return -1;
136 
137  dbg = d->dbg;
138  dbg->rttchan = c;
139  atomic_set(&dbg->rttseq, 0);
140 
141  return 0;
142 }
143 
144 static void
145 rttstop(struct ddbg *dbg)
146 {
147  if (!dbg->rttchan)
148  return;
149 
150  relay_flush(dbg->rttchan);
151  relay_close(dbg->rttchan);
152  dbg->rttchan = NULL;
153 }
154 
155 /* called from code that can sleep */
156 void
158 {
159  struct ddbg *dbg;
160  unsigned long flags;
161 
162  if (!AOEDBG_ACTIVE)
163  return;
164 
165  dbg = aoe_kcalloc(1, sizeof *dbg, GFP_KERNEL);
166  if (!dbg) {
167  printk(KERN_ERR
168  "aoe: could not allocate memory to debug e%ld.%d\n",
169  d->aoemajor, d->aoeminor);
170  return;
171  }
172  spin_lock_irqsave(&d->lock, flags);
173  if (d->dbg || (d->flags & DEVFL_TKILL)) {
174  spin_unlock_irqrestore(&d->lock, flags);
175  kfree(dbg);
176  return;
177  }
178  d->dbg = dbg;
179  spin_unlock_irqrestore(&d->lock, flags);
180 
181  if (!rttstart(d))
182  return;
183  d->dbg = NULL;
184  kfree(dbg);
185 }
186 
187 void
188 aoedbg_rtt(struct aoedev *d, struct aoe_hdr *h, struct frame *f, int rtt)
189 {
190  struct timeval now;
191  enum recflags {
192  R_ORPHAN = 1,
193  R_WRITE = 1 << 1,
194  };
195  struct ddbg *dbg;
196  struct aoe_atahdr *ah;
197  struct record {
198  u32 seqno;
199  u32 rtt;
200  u32 reltime;
201  u32 rttavg;
202  u32 rttdev;
203  u8 send_nout;
204  u8 rcv_nout;
205  u8 ssthresh;
206  u8 cwnd;
207  u8 lba0;
208  u8 lba1;
209  u8 lba2;
210  u8 lba3;
211  u8 lba4;
212  u8 lba5;
213  u8 flags;
214  u8 remote[6];
215  u8 local[6];
216  } __attribute__ ((packed)) r = { 0, };
217 
218  dbg = d->dbg;
219 
220  if (!dbg || !dbg->rttchan)
221  return;
222 
223  ah = (struct aoe_atahdr *)(h + 1);
224  r.seqno = (u32) atomic_inc_return(&dbg->rttseq);
225  r.rtt = (u32) rtt;
226  do_gettimeofday(&now);
227  r.reltime = now.tv_usec - start.tv_usec;
228  r.reltime += (now.tv_sec - start.tv_sec) * USEC_PER_SEC;
229  r.rttavg = d->rttavg >> RTTSCALE;
230  r.rttdev = d->rttdev >> RTTDSCALE;
231  if (!f) {
232  r.flags |= R_ORPHAN;
233  } else {
234  r.send_nout = f->nout;
235  r.rcv_nout = f->t->nout;
236  r.ssthresh = f->t->ssthresh;
237  r.cwnd = f->t->maxout;
238  }
239  r.lba0 = ah->lba0;
240  r.lba1 = ah->lba1;
241  r.lba2 = ah->lba2;
242  r.lba3 = ah->lba3;
243  r.lba4 = ah->lba4;
244  r.lba5 = ah->lba5;
245  r.flags |= !!(ah->aflags & AOEAFL_WRITE);
246  memmove(r.remote, h->src, sizeof r.remote);
247  memmove(r.local, h->dst, sizeof r.local);
248 
249  relay_write(dbg->rttchan, &r, sizeof r);
250 }
251 
252 void
254 {
255  struct ddbg *dbg;
256 
257  dbg = (struct ddbg *) d->dbg;
258 
259  if (!dbg)
260  return;
261 
262  rttstop(dbg);
263  kfree(dbg);
264  d->dbg = NULL;
265 }
266 
267 void
269 {
270  if (chan)
271  relay_close(chan);
272 }
aoe_atahdr::lba3
unsigned char lba3
Definition: aoe.h:59
aoe_hdr::src
unsigned char src[6]
Definition: aoe.h:41
aoe_atahdr::aflags
unsigned char aflags
Definition: aoe.h:52
aoe_atahdr::lba5
unsigned char lba5
Definition: aoe.h:61
frame::nout
ushort nout
Definition: aoe.h:126
DEFINE_SPINLOCK
static DEFINE_SPINLOCK(buflock)
aoedev::rttdev
u32 rttdev
Definition: aoe.h:160
aoetgt::nout
ushort nout
Definition: aoe.h:143
u32
uint32_t u32
Definition: dat.h:20
N_SUBBUFS
#define N_SUBBUFS
Definition: aoedbg.c:9
aoe_kcalloc
void * aoe_kcalloc(size_t, size_t, int)
Definition: aoemain.c:32
aoedbg_exit
void aoedbg_exit(void)
Definition: aoedbg.c:268
SUBBUF_SIZE
#define SUBBUF_SIZE
Definition: aoedbg.c:8
cfile
static struct dentry * cfile(const char *filename, struct dentry *parent, umode_t mode, struct rchan_buf *buf, int *is_global)
Definition: aoedbg.c:27
aoe_atahdr::lba0
unsigned char lba0
Definition: aoe.h:56
aoetgt::ssthresh
ushort ssthresh
Definition: aoe.h:146
subbuf_start
static int subbuf_start(struct rchan_buf *buf, void *subbuf, void *prev_subbuf, size_t prev_padding)
Definition: aoedbg.c:44
aoe_hdr::dst
unsigned char dst[6]
Definition: aoe.h:40
aoedbg_write
static void aoedbg_write(const void *data, size_t length)
Definition: aoedbg.c:97
aoe_atahdr::lba1
unsigned char lba1
Definition: aoe.h:57
ddbg::rttseq
atomic_t rttseq
Definition: aoedbg.c:19
frame
Definition: aoe.h:114
AOEDBG_ACTIVE
#define AOEDBG_ACTIVE
Definition: aoe.h:258
aoe.h
aoedbg_rtt
void aoedbg_rtt(struct aoedev *d, struct aoe_hdr *h, struct frame *f, int rtt)
Definition: aoedbg.c:188
rttstart
static int rttstart(struct aoedev *d)
Definition: aoedbg.c:124
ddbg::rttchan
struct rchan * rttchan
Definition: aoedbg.c:18
ddbg
Definition: aoedbg.c:17
aoedev::flags
u16 flags
Definition: aoe.h:162
rfile
static int rfile(struct dentry *dentry)
Definition: aoedbg.c:37
rttstop
static void rttstop(struct ddbg *dbg)
Definition: aoedbg.c:145
aoedev::lock
spinlock_t lock
Definition: aoe.h:175
aoedev::dbg
void * dbg
Definition: aoe.h:192
aoe_atahdr::lba2
unsigned char lba2
Definition: aoe.h:58
buf
Definition: aoe.h:103
aoedbg_print
void aoedbg_print(char *fmt,...)
Definition: aoedbg.c:107
xrelay_open
static struct rchan * xrelay_open(const char *base_fnam, struct dentry *parent, size_t subbuf_size, size_t n_subbufs)
Definition: aoedbg.c:59
RTTDSCALE
Definition: aoe.h:95
aoedev
Definition: aoe.h:155
chan
static struct rchan * chan
Definition: aoedbg.c:12
AOEAFL_WRITE
Definition: aoe.h:28
aoetgt::maxout
ushort maxout
Definition: aoe.h:144
aoedev::aoemajor
ulong aoemajor
Definition: aoe.h:158
aoedbg_init
void __init aoedbg_init(void)
Definition: aoedbg.c:80
aoe_atahdr
Definition: aoe.h:51
start
static struct timeval start
Definition: aoedbg.c:14
aoe_atahdr::lba4
unsigned char lba4
Definition: aoe.h:60
cb
static struct rchan_callbacks cb
Definition: aoedbg.c:51
aoedbg_devinit
void aoedbg_devinit(struct aoedev *d)
Definition: aoedbg.c:157
aoedev::rttavg
u32 rttavg
Definition: aoe.h:159
DEVFL_TKILL
Definition: aoe.h:75
aoedev::aoeminor
u16 aoeminor
Definition: aoe.h:161
aoe_hdr
Definition: aoe.h:39
RTTSCALE
Definition: aoe.h:94
aoedbg_undbg
void aoedbg_undbg(struct aoedev *d)
Definition: aoedbg.c:253
frame::t
struct aoetgt * t
Definition: aoe.h:121