blob: dcec2e4f84ad4c7bfe88efeaa051b324e9521dd0 [file] [log] [blame]
Kent Overstreetcafe5632013-03-23 16:11:31 -07001/*
2 * random utiility code, for bcache but in theory not specific to bcache
3 *
4 * Copyright 2010, 2011 Kent Overstreet <kent.overstreet@gmail.com>
5 * Copyright 2012 Google, Inc.
6 */
7
8#include <linux/bio.h>
9#include <linux/blkdev.h>
10#include <linux/ctype.h>
11#include <linux/debugfs.h>
12#include <linux/module.h>
13#include <linux/seq_file.h>
14#include <linux/types.h>
15
16#include "util.h"
17
18#define simple_strtoint(c, end, base) simple_strtol(c, end, base)
19#define simple_strtouint(c, end, base) simple_strtoul(c, end, base)
20
21#define STRTO_H(name, type) \
22int name ## _h(const char *cp, type *res) \
23{ \
24 int u = 0; \
25 char *e; \
26 type i = simple_ ## name(cp, &e, 10); \
27 \
28 switch (tolower(*e)) { \
29 default: \
30 return -EINVAL; \
31 case 'y': \
32 case 'z': \
33 u++; \
34 case 'e': \
35 u++; \
36 case 'p': \
37 u++; \
38 case 't': \
39 u++; \
40 case 'g': \
41 u++; \
42 case 'm': \
43 u++; \
44 case 'k': \
45 u++; \
46 if (e++ == cp) \
47 return -EINVAL; \
48 case '\n': \
49 case '\0': \
50 if (*e == '\n') \
51 e++; \
52 } \
53 \
54 if (*e) \
55 return -EINVAL; \
56 \
57 while (u--) { \
58 if ((type) ~0 > 0 && \
59 (type) ~0 / 1024 <= i) \
60 return -EINVAL; \
61 if ((i > 0 && ANYSINT_MAX(type) / 1024 < i) || \
62 (i < 0 && -ANYSINT_MAX(type) / 1024 > i)) \
63 return -EINVAL; \
64 i *= 1024; \
65 } \
66 \
67 *res = i; \
68 return 0; \
69} \
70EXPORT_SYMBOL_GPL(name ## _h);
71
72STRTO_H(strtoint, int)
73STRTO_H(strtouint, unsigned int)
74STRTO_H(strtoll, long long)
75STRTO_H(strtoull, unsigned long long)
76
77ssize_t hprint(char *buf, int64_t v)
78{
79 static const char units[] = "?kMGTPEZY";
80 char dec[3] = "";
81 int u, t = 0;
82
83 for (u = 0; v >= 1024 || v <= -1024; u++) {
84 t = v & ~(~0 << 10);
85 v >>= 10;
86 }
87
88 if (!u)
89 return sprintf(buf, "%llu", v);
90
91 if (v < 100 && v > -100)
92 sprintf(dec, ".%i", t / 100);
93
94 return sprintf(buf, "%lli%s%c", v, dec, units[u]);
95}
96EXPORT_SYMBOL_GPL(hprint);
97
98ssize_t snprint_string_list(char *buf, size_t size, const char * const list[],
99 size_t selected)
100{
101 char *out = buf;
102 size_t i;
103
104 for (i = 0; list[i]; i++)
105 out += snprintf(out, buf + size - out,
106 i == selected ? "[%s] " : "%s ", list[i]);
107
108 out[-1] = '\n';
109 return out - buf;
110}
111EXPORT_SYMBOL_GPL(snprint_string_list);
112
113ssize_t read_string_list(const char *buf, const char * const list[])
114{
115 size_t i;
116 char *s, *d = kstrndup(buf, PAGE_SIZE - 1, GFP_KERNEL);
117 if (!d)
118 return -ENOMEM;
119
120 s = strim(d);
121
122 for (i = 0; list[i]; i++)
123 if (!strcmp(list[i], s))
124 break;
125
126 kfree(d);
127
128 if (!list[i])
129 return -EINVAL;
130
131 return i;
132}
133EXPORT_SYMBOL_GPL(read_string_list);
134
135bool is_zero(const char *p, size_t n)
136{
137 size_t i;
138
139 for (i = 0; i < n; i++)
140 if (p[i])
141 return false;
142 return true;
143}
144EXPORT_SYMBOL_GPL(is_zero);
145
146int parse_uuid(const char *s, char *uuid)
147{
148 size_t i, j, x;
149 memset(uuid, 0, 16);
150
151 for (i = 0, j = 0;
152 i < strspn(s, "-0123456789:ABCDEFabcdef") && j < 32;
153 i++) {
154 x = s[i] | 32;
155
156 switch (x) {
157 case '0'...'9':
158 x -= '0';
159 break;
160 case 'a'...'f':
161 x -= 'a' - 10;
162 break;
163 default:
164 continue;
165 }
166
167 if (!(j & 1))
168 x <<= 4;
169 uuid[j++ >> 1] |= x;
170 }
171 return i;
172}
173EXPORT_SYMBOL_GPL(parse_uuid);
174
175void time_stats_update(struct time_stats *stats, uint64_t start_time)
176{
177 uint64_t now = local_clock();
178 uint64_t duration = time_after64(now, start_time)
179 ? now - start_time : 0;
180 uint64_t last = time_after64(now, stats->last)
181 ? now - stats->last : 0;
182
183 stats->max_duration = max(stats->max_duration, duration);
184
185 if (stats->last) {
186 ewma_add(stats->average_duration, duration, 8, 8);
187
188 if (stats->average_frequency)
189 ewma_add(stats->average_frequency, last, 8, 8);
190 else
191 stats->average_frequency = last << 8;
192 } else {
193 stats->average_duration = duration << 8;
194 }
195
196 stats->last = now ?: 1;
197}
198EXPORT_SYMBOL_GPL(time_stats_update);
199
200unsigned next_delay(struct ratelimit *d, uint64_t done)
201{
202 uint64_t now = local_clock();
203
204 d->next += div_u64(done, d->rate);
205
206 return time_after64(d->next, now)
207 ? div_u64(d->next - now, NSEC_PER_SEC / HZ)
208 : 0;
209}
210EXPORT_SYMBOL_GPL(next_delay);
211
212void bio_map(struct bio *bio, void *base)
213{
214 size_t size = bio->bi_size;
215 struct bio_vec *bv = bio->bi_io_vec;
216
217 BUG_ON(!bio->bi_size);
218 BUG_ON(bio->bi_vcnt);
219
220 bv->bv_offset = base ? ((unsigned long) base) % PAGE_SIZE : 0;
221 goto start;
222
223 for (; size; bio->bi_vcnt++, bv++) {
224 bv->bv_offset = 0;
225start: bv->bv_len = min_t(size_t, PAGE_SIZE - bv->bv_offset,
226 size);
227 if (base) {
228 bv->bv_page = is_vmalloc_addr(base)
229 ? vmalloc_to_page(base)
230 : virt_to_page(base);
231
232 base += bv->bv_len;
233 }
234
235 size -= bv->bv_len;
236 }
237}
238EXPORT_SYMBOL_GPL(bio_map);
239
240int bio_alloc_pages(struct bio *bio, gfp_t gfp)
241{
242 int i;
243 struct bio_vec *bv;
244
245 bio_for_each_segment(bv, bio, i) {
246 bv->bv_page = alloc_page(gfp);
247 if (!bv->bv_page) {
248 while (bv-- != bio->bi_io_vec + bio->bi_idx)
249 __free_page(bv->bv_page);
250 return -ENOMEM;
251 }
252 }
253
254 return 0;
255}
256EXPORT_SYMBOL_GPL(bio_alloc_pages);
257
258/*
259 * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group (Any
260 * use permitted, subject to terms of PostgreSQL license; see.)
261
262 * If we have a 64-bit integer type, then a 64-bit CRC looks just like the
263 * usual sort of implementation. (See Ross Williams' excellent introduction
264 * A PAINLESS GUIDE TO CRC ERROR DETECTION ALGORITHMS, available from
265 * ftp://ftp.rocksoft.com/papers/crc_v3.txt or several other net sites.)
266 * If we have no working 64-bit type, then fake it with two 32-bit registers.
267 *
268 * The present implementation is a normal (not "reflected", in Williams'
269 * terms) 64-bit CRC, using initial all-ones register contents and a final
270 * bit inversion. The chosen polynomial is borrowed from the DLT1 spec
271 * (ECMA-182, available from http://www.ecma.ch/ecma1/STAND/ECMA-182.HTM):
272 *
273 * x^64 + x^62 + x^57 + x^55 + x^54 + x^53 + x^52 + x^47 + x^46 + x^45 +
274 * x^40 + x^39 + x^38 + x^37 + x^35 + x^33 + x^32 + x^31 + x^29 + x^27 +
275 * x^24 + x^23 + x^22 + x^21 + x^19 + x^17 + x^13 + x^12 + x^10 + x^9 +
276 * x^7 + x^4 + x + 1
277*/
278
279static const uint64_t crc_table[256] = {
280 0x0000000000000000, 0x42F0E1EBA9EA3693, 0x85E1C3D753D46D26,
281 0xC711223CFA3E5BB5, 0x493366450E42ECDF, 0x0BC387AEA7A8DA4C,
282 0xCCD2A5925D9681F9, 0x8E224479F47CB76A, 0x9266CC8A1C85D9BE,
283 0xD0962D61B56FEF2D, 0x17870F5D4F51B498, 0x5577EEB6E6BB820B,
284 0xDB55AACF12C73561, 0x99A54B24BB2D03F2, 0x5EB4691841135847,
285 0x1C4488F3E8F96ED4, 0x663D78FF90E185EF, 0x24CD9914390BB37C,
286 0xE3DCBB28C335E8C9, 0xA12C5AC36ADFDE5A, 0x2F0E1EBA9EA36930,
287 0x6DFEFF5137495FA3, 0xAAEFDD6DCD770416, 0xE81F3C86649D3285,
288 0xF45BB4758C645C51, 0xB6AB559E258E6AC2, 0x71BA77A2DFB03177,
289 0x334A9649765A07E4, 0xBD68D2308226B08E, 0xFF9833DB2BCC861D,
290 0x388911E7D1F2DDA8, 0x7A79F00C7818EB3B, 0xCC7AF1FF21C30BDE,
291 0x8E8A101488293D4D, 0x499B3228721766F8, 0x0B6BD3C3DBFD506B,
292 0x854997BA2F81E701, 0xC7B97651866BD192, 0x00A8546D7C558A27,
293 0x4258B586D5BFBCB4, 0x5E1C3D753D46D260, 0x1CECDC9E94ACE4F3,
294 0xDBFDFEA26E92BF46, 0x990D1F49C77889D5, 0x172F5B3033043EBF,
295 0x55DFBADB9AEE082C, 0x92CE98E760D05399, 0xD03E790CC93A650A,
296 0xAA478900B1228E31, 0xE8B768EB18C8B8A2, 0x2FA64AD7E2F6E317,
297 0x6D56AB3C4B1CD584, 0xE374EF45BF6062EE, 0xA1840EAE168A547D,
298 0x66952C92ECB40FC8, 0x2465CD79455E395B, 0x3821458AADA7578F,
299 0x7AD1A461044D611C, 0xBDC0865DFE733AA9, 0xFF3067B657990C3A,
300 0x711223CFA3E5BB50, 0x33E2C2240A0F8DC3, 0xF4F3E018F031D676,
301 0xB60301F359DBE0E5, 0xDA050215EA6C212F, 0x98F5E3FE438617BC,
302 0x5FE4C1C2B9B84C09, 0x1D14202910527A9A, 0x93366450E42ECDF0,
303 0xD1C685BB4DC4FB63, 0x16D7A787B7FAA0D6, 0x5427466C1E109645,
304 0x4863CE9FF6E9F891, 0x0A932F745F03CE02, 0xCD820D48A53D95B7,
305 0x8F72ECA30CD7A324, 0x0150A8DAF8AB144E, 0x43A04931514122DD,
306 0x84B16B0DAB7F7968, 0xC6418AE602954FFB, 0xBC387AEA7A8DA4C0,
307 0xFEC89B01D3679253, 0x39D9B93D2959C9E6, 0x7B2958D680B3FF75,
308 0xF50B1CAF74CF481F, 0xB7FBFD44DD257E8C, 0x70EADF78271B2539,
309 0x321A3E938EF113AA, 0x2E5EB66066087D7E, 0x6CAE578BCFE24BED,
310 0xABBF75B735DC1058, 0xE94F945C9C3626CB, 0x676DD025684A91A1,
311 0x259D31CEC1A0A732, 0xE28C13F23B9EFC87, 0xA07CF2199274CA14,
312 0x167FF3EACBAF2AF1, 0x548F120162451C62, 0x939E303D987B47D7,
313 0xD16ED1D631917144, 0x5F4C95AFC5EDC62E, 0x1DBC74446C07F0BD,
314 0xDAAD56789639AB08, 0x985DB7933FD39D9B, 0x84193F60D72AF34F,
315 0xC6E9DE8B7EC0C5DC, 0x01F8FCB784FE9E69, 0x43081D5C2D14A8FA,
316 0xCD2A5925D9681F90, 0x8FDAB8CE70822903, 0x48CB9AF28ABC72B6,
317 0x0A3B7B1923564425, 0x70428B155B4EAF1E, 0x32B26AFEF2A4998D,
318 0xF5A348C2089AC238, 0xB753A929A170F4AB, 0x3971ED50550C43C1,
319 0x7B810CBBFCE67552, 0xBC902E8706D82EE7, 0xFE60CF6CAF321874,
320 0xE224479F47CB76A0, 0xA0D4A674EE214033, 0x67C58448141F1B86,
321 0x253565A3BDF52D15, 0xAB1721DA49899A7F, 0xE9E7C031E063ACEC,
322 0x2EF6E20D1A5DF759, 0x6C0603E6B3B7C1CA, 0xF6FAE5C07D3274CD,
323 0xB40A042BD4D8425E, 0x731B26172EE619EB, 0x31EBC7FC870C2F78,
324 0xBFC9838573709812, 0xFD39626EDA9AAE81, 0x3A28405220A4F534,
325 0x78D8A1B9894EC3A7, 0x649C294A61B7AD73, 0x266CC8A1C85D9BE0,
326 0xE17DEA9D3263C055, 0xA38D0B769B89F6C6, 0x2DAF4F0F6FF541AC,
327 0x6F5FAEE4C61F773F, 0xA84E8CD83C212C8A, 0xEABE6D3395CB1A19,
328 0x90C79D3FEDD3F122, 0xD2377CD44439C7B1, 0x15265EE8BE079C04,
329 0x57D6BF0317EDAA97, 0xD9F4FB7AE3911DFD, 0x9B041A914A7B2B6E,
330 0x5C1538ADB04570DB, 0x1EE5D94619AF4648, 0x02A151B5F156289C,
331 0x4051B05E58BC1E0F, 0x87409262A28245BA, 0xC5B073890B687329,
332 0x4B9237F0FF14C443, 0x0962D61B56FEF2D0, 0xCE73F427ACC0A965,
333 0x8C8315CC052A9FF6, 0x3A80143F5CF17F13, 0x7870F5D4F51B4980,
334 0xBF61D7E80F251235, 0xFD913603A6CF24A6, 0x73B3727A52B393CC,
335 0x31439391FB59A55F, 0xF652B1AD0167FEEA, 0xB4A25046A88DC879,
336 0xA8E6D8B54074A6AD, 0xEA16395EE99E903E, 0x2D071B6213A0CB8B,
337 0x6FF7FA89BA4AFD18, 0xE1D5BEF04E364A72, 0xA3255F1BE7DC7CE1,
338 0x64347D271DE22754, 0x26C49CCCB40811C7, 0x5CBD6CC0CC10FAFC,
339 0x1E4D8D2B65FACC6F, 0xD95CAF179FC497DA, 0x9BAC4EFC362EA149,
340 0x158E0A85C2521623, 0x577EEB6E6BB820B0, 0x906FC95291867B05,
341 0xD29F28B9386C4D96, 0xCEDBA04AD0952342, 0x8C2B41A1797F15D1,
342 0x4B3A639D83414E64, 0x09CA82762AAB78F7, 0x87E8C60FDED7CF9D,
343 0xC51827E4773DF90E, 0x020905D88D03A2BB, 0x40F9E43324E99428,
344 0x2CFFE7D5975E55E2, 0x6E0F063E3EB46371, 0xA91E2402C48A38C4,
345 0xEBEEC5E96D600E57, 0x65CC8190991CB93D, 0x273C607B30F68FAE,
346 0xE02D4247CAC8D41B, 0xA2DDA3AC6322E288, 0xBE992B5F8BDB8C5C,
347 0xFC69CAB42231BACF, 0x3B78E888D80FE17A, 0x7988096371E5D7E9,
348 0xF7AA4D1A85996083, 0xB55AACF12C735610, 0x724B8ECDD64D0DA5,
349 0x30BB6F267FA73B36, 0x4AC29F2A07BFD00D, 0x08327EC1AE55E69E,
350 0xCF235CFD546BBD2B, 0x8DD3BD16FD818BB8, 0x03F1F96F09FD3CD2,
351 0x41011884A0170A41, 0x86103AB85A2951F4, 0xC4E0DB53F3C36767,
352 0xD8A453A01B3A09B3, 0x9A54B24BB2D03F20, 0x5D45907748EE6495,
353 0x1FB5719CE1045206, 0x919735E51578E56C, 0xD367D40EBC92D3FF,
354 0x1476F63246AC884A, 0x568617D9EF46BED9, 0xE085162AB69D5E3C,
355 0xA275F7C11F7768AF, 0x6564D5FDE549331A, 0x279434164CA30589,
356 0xA9B6706FB8DFB2E3, 0xEB46918411358470, 0x2C57B3B8EB0BDFC5,
357 0x6EA7525342E1E956, 0x72E3DAA0AA188782, 0x30133B4B03F2B111,
358 0xF7021977F9CCEAA4, 0xB5F2F89C5026DC37, 0x3BD0BCE5A45A6B5D,
359 0x79205D0E0DB05DCE, 0xBE317F32F78E067B, 0xFCC19ED95E6430E8,
360 0x86B86ED5267CDBD3, 0xC4488F3E8F96ED40, 0x0359AD0275A8B6F5,
361 0x41A94CE9DC428066, 0xCF8B0890283E370C, 0x8D7BE97B81D4019F,
362 0x4A6ACB477BEA5A2A, 0x089A2AACD2006CB9, 0x14DEA25F3AF9026D,
363 0x562E43B4931334FE, 0x913F6188692D6F4B, 0xD3CF8063C0C759D8,
364 0x5DEDC41A34BBEEB2, 0x1F1D25F19D51D821, 0xD80C07CD676F8394,
365 0x9AFCE626CE85B507
366};
367
368uint64_t crc64_update(uint64_t crc, const void *_data, size_t len)
369{
370 const unsigned char *data = _data;
371
372 while (len--) {
373 int i = ((int) (crc >> 56) ^ *data++) & 0xFF;
374 crc = crc_table[i] ^ (crc << 8);
375 }
376
377 return crc;
378}
379EXPORT_SYMBOL(crc64_update);
380
381uint64_t crc64(const void *data, size_t len)
382{
383 uint64_t crc = 0xffffffffffffffff;
384
385 crc = crc64_update(crc, data, len);
386
387 return crc ^ 0xffffffffffffffff;
388}
389EXPORT_SYMBOL(crc64);