aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
Diffstat (limited to 'drivers')
-rw-r--r--drivers/staging/cowloop/cowloop.c2897
-rw-r--r--drivers/staging/cowloop/cowloop.h66
2 files changed, 2963 insertions, 0 deletions
diff --git a/drivers/staging/cowloop/cowloop.c b/drivers/staging/cowloop/cowloop.c
new file mode 100644
index 000000000000..23978012838a
--- /dev/null
+++ b/drivers/staging/cowloop/cowloop.c
@@ -0,0 +1,2897 @@
1/*
2** COWLOOP block device driver (2.6 kernel compliant)
3** =======================================================================
4** Read-write loop-driver with copy-on-write functionality.
5**
6** Synopsis:
7**
8** modprobe cowloop [maxcows=..] [rdofile=..... cowfile=.... [option=r]]
9**
10** Definition of number of configured cowdevices:
11** maxcows= number of configured cowdevices (default: 16)
12** (do not confuse this with MAXCOWS: absolute maximum as compiled)
13**
14** One pair of filenames can be supplied during insmod/modprobe to open
15** the first cowdevice:
16** rdofile= read-only file (or filesystem)
17** cowfile= storage-space for modified blocks of read-only file(system)
18** option=r repair cowfile automatically if it appears to be dirty
19**
20** Other cowdevices can be activated via the command "cowdev"
21** whenever the cowloop-driver is loaded.
22**
23** The read-only file may be of type 'regular' or 'block-device'.
24**
25** The cowfile must be of type 'regular'.
26** If an existing regular file is used as cowfile, its contents will be
27** used again for the current read-only file. When the cowfile has not been
28** closed properly during a previous session (i.e. rmmod cowloop), the
29** cowloop-driver refuses to open it unless the parameter "option=r" is
30** specified.
31**
32** Layout of cowfile:
33**
34** +-----------------------------+
35** | cow head block | MAPUNIT bytes
36** |-----------------------------|
37** | | MAPUNIT bytes
38** |--- ---|
39** | | MAPUNIT bytes
40** |--- ---|
41** | used-block bitmap | MAPUNIT bytes
42** |-----------------------------|
43** | gap to align start-offset |
44** | to 4K multiple |
45** |-----------------------------| <---- start-offset cow blocks
46** | |
47** | written cow blocks | MAPUNIT bytes
48** | ..... |
49**
50** cowhead block:
51** - contains general info about the rdofile which is related
52** to this cowfile
53**
54** used-block bitmap:
55** - contains one bit per block with a size of MAPUNIT bytes
56** - bit-value '1' = block has been written on cow
57** '0' = block unused on cow
58** - total bitmap rounded to multiples of MAPUNIT
59**
60** ============================================================================
61** Author: Gerlof Langeveld - AT Computing (March 2003)
62** Current maintainer: Hendrik-Jan Thomassen - AT Computing (Summer 2006)
63** Email: hjt@ATComputing.nl
64** ----------------------------------------------------------------------------
65** Copyright (C) 2003-2009 AT Consultancy
66**
67** This program is free software; you can redistribute it and/or modify it
68** under the terms of the GNU General Public License as published by the
69** Free Software Foundation; either version 2, or (at your option) any
70** later version.
71**
72** This program is distributed in the hope that it will be useful, but
73** WITHOUT ANY WARRANTY; without even the implied warranty of
74** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
75** See the GNU General Public License for more details.
76**
77** You should have received a copy of the GNU General Public License
78** along with this program; if not, write to the Free Software
79** Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
80** ----------------------------------------------------------------------------
81**
82** Major modifications:
83**
84** 200405 Ported to kernel-version 2.6 Hendrik-Jan Thomassen
85** 200405 Added cowhead to cowfile to garantee
86** consistency with read-only file Gerlof Langeveld
87** 200405 Postponed flushing of bitmaps to improve
88** performance. Gerlof Langeveld
89** 200405 Inline recovery for dirty cowfiles. Gerlof Langeveld
90** 200502 Redesign to support more cowdevices. Gerlof Langeveld
91** 200502 Support devices/file > 2 Gbytes. Gerlof Langeveld
92** 200507 Check for free space to expand cowfile. Gerlof Langeveld
93** 200902 Upgrade for kernel 2.6.28 Hendrik-Jan Thomassen
94**
95** Inspired by
96** loop.c by Theodore Ts'o and
97** cloop.c by Paul `Rusty' Russell & Klaus Knopper.
98**
99** Design-considerations:
100**
101** For the first experiments with the cowloop-driver, the request-queue
102** made use of the do_generic_file_read() which worked fine except
103** in combination with the cloop-driver; that combination
104** resulted in a non-interruptible hangup of the system during
105** heavy load. Other experiments using the `make_request' interface also
106** resulted in unpredictable system hangups (with proper use of spinlocks).
107**
108** To overcome these problems, the cowloop-driver starts a kernel-thread
109** for every active cowdevice.
110** All read- and write-request on the read-only file and copy-on-write file
111** are handled in the context of that thread.
112** A scheme has been designed to wakeup the kernel-thread as
113** soon as I/O-requests are available in the request-queue; this thread
114** handles the requests one-by-one by calling the proper read- or
115** write-function related to the open read-only file or copy-on-write file.
116** When all pending requests have been handled, the kernel-thread goes
117** back to sleep-state.
118** This approach requires some additional context-switches; however the
119** performance loss during heavy I/O is less than 3%.
120**
121** -------------------------------------------------------------------------*/
122/* The following is the cowloop package version number. It must be
123 identical to the content of the include-file "version.h" that is
124 used in all supporting utilities: */
125char revision[] = "$Revision: 3.1 $"; /* cowlo_init_module() has
126 assumptions about this string's format */
127
128/* Note that the following numbers are *not* the cowloop package version
129 numbers, but separate revision history numbers to track the
130 modifications of this particular source file: */
131/* $Log: cowloop.c,v $
132**
133** Revision 1.30 2009/02/08 hjt
134** Integrated earlier fixes
135** Upgraded to kernel 2.6.28 (thanks Jerome Poulin)
136**
137** Revision 1.29 2006/12/03 22:12:00 hjt
138** changed 'cowdevlock' from spinlock to semaphore, to avoid
139** "scheduling while atomic". Contributed by Juergen Christ.
140** Added version.h again
141**
142** Revision 1.28 2006/08/16 16:00:00 hjt
143** malloc each individual cowloopdevice struct separately
144**
145** Revision 1.27 2006/03/14 14:57:03 root
146** Removed include version.h
147**
148** Revision 1.26 2005/08/08 11:22:48 root
149** Implement possibility to close a cow file or reopen a cowfile read-only.
150**
151** Revision 1.25 2005/08/03 14:00:39 root
152** Added modinfo info to driver.
153**
154** Revision 1.24 2005/07/21 06:14:53 root
155** Cosmetic changes source code.
156**
157** Revision 1.23 2005/07/20 13:07:32 root
158** Supply ioctl to write watchdog program to react on lack of cowfile space.
159**
160** Revision 1.22 2005/07/20 07:53:34 root
161** Regular verification of free space in filesystem holding the cowfile
162** (give warnings whenever space is almost exhausted).
163** Terminology change: checksum renamed to fingerprint.
164**
165** Revision 1.21 2005/07/19 09:21:52 root
166** Removing maximum limit of 16 Gb per cowdevice.
167**
168** Revision 1.20 2005/07/19 07:50:33 root
169** Minor bugfixes and cosmetic changes.
170**
171** Revision 1.19 2005/06/10 12:29:55 root
172** Removed lock/unlock operation from cowlo_open().
173**
174** Revision 1.18 2005/05/09 12:56:26 root
175** Allow a cowdevice to be open more than once
176** (needed for support of ReiserFS and XFS).
177**
178** Revision 1.17 2005/03/17 14:36:16 root
179** Fixed some license issues.
180**
181** Revision 1.16 2005/03/07 14:42:05 root
182** Only allow one parallel open per cowdevice.
183**
184** Revision 1.15 2005/02/18 11:52:04 gerlof
185** Redesign to support more than one cowdevice > 2 Gb space.
186**
187** Revision 1.14 2004/08/17 14:19:16 gerlof
188** Modified output of /proc/cowloop.
189**
190** Revision 1.13 2004/08/16 07:21:10 gerlof
191** Separate statistical counter for read on rdofile and cowfile.
192**
193** Revision 1.12 2004/08/11 06:52:11 gerlof
194** Modified messages.
195**
196** Revision 1.11 2004/08/11 06:44:11 gerlof
197** Modified log messages.
198**
199** Revision 1.10 2004/08/10 12:27:27 gerlof
200** Cosmetic changes.
201**
202** Revision 1.9 2004/08/09 11:43:37 gerlof
203** Removed double definition of major number (COWMAJOR).
204**
205** Revision 1.8 2004/08/09 08:03:39 gerlof
206** Cleanup of messages.
207**
208** Revision 1.7 2004/05/27 06:37:33 gerlof
209** Modified /proc message.
210**
211** Revision 1.6 2004/05/26 21:23:28 gerlof
212** Modified /proc output.
213**
214** Revision 1.5 2004/05/26 13:23:34 gerlof
215** Support cowsync to force flushing the bitmaps and cowhead.
216**
217** Revision 1.4 2004/05/26 11:11:10 gerlof
218** Updated the comment to the actual situation.
219**
220** Revision 1.3 2004/05/26 10:50:00 gerlof
221** Implemented recovery-option.
222**
223** Revision 1.2 2004/05/25 15:14:41 gerlof
224** Modified bitmap flushing strategy.
225**
226*/
227
228#define COWMAJOR 241
229
230// #define COWDEBUG
231
232#ifdef COWDEBUG
233#define DEBUGP printk
234#define DCOW KERN_ALERT
235#else
236#define DEBUGP(format, x...)
237#endif
238
239#include <linux/types.h>
240#include <linux/autoconf.h>
241#ifndef AUTOCONF_INCLUDED
242#include <linux/config.h>
243#endif
244#include <linux/module.h>
245#include <linux/version.h>
246#include <linux/moduleparam.h>
247#include <linux/init.h>
248#include <linux/errno.h>
249#include <linux/kernel.h>
250#include <linux/major.h>
251#include <linux/sched.h>
252#include <linux/fs.h>
253#include <linux/file.h>
254#include <linux/stat.h>
255#include <linux/vmalloc.h>
256#include <linux/slab.h>
257#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,27))
258#include <linux/semaphore.h>
259#else
260#include <asm/semaphore.h>
261#endif
262#include <asm/uaccess.h>
263#include <linux/proc_fs.h>
264#include <linux/blkdev.h>
265#include <linux/buffer_head.h>
266#include <linux/hdreg.h>
267#include <linux/genhd.h>
268#include <linux/statfs.h>
269
270#include "cowloop.h"
271
272MODULE_LICENSE("GPL");
273/* MODULE_AUTHOR("Gerlof Langeveld <gerlof@ATComputing.nl>"); obsolete address */
274MODULE_AUTHOR("Hendrik-Jan Thomassen <hjt@ATComputing.nl>"); /* current maintainer */
275MODULE_DESCRIPTION("Copy-on-write loop driver");
276MODULE_PARM_DESC(maxcows, " Number of configured cowdevices (default 16)");
277MODULE_PARM_DESC(rdofile, " Read-only file for /dev/cow/0");
278MODULE_PARM_DESC(cowfile, " Cowfile for /dev/cow/0");
279MODULE_PARM_DESC(option, " Repair cowfile if inconsistent: option=r");
280
281#define DEVICE_NAME "cow"
282
283#define DFLCOWS 16 /* default cowloop devices */
284
285static int maxcows = DFLCOWS;
286module_param(maxcows, int, 0);
287static char *rdofile = "";
288module_param(rdofile, charp, 0);
289static char *cowfile = "";
290module_param(cowfile, charp, 0);
291static char *option = "";
292module_param(option, charp, 0);
293
294/*
295** per cowdevice several bitmap chunks are allowed of MAPCHUNKSZ each
296**
297** each bitmap chunk can describe MAPCHUNKSZ * 8 * MAPUNIT bytes of data
298** suppose:
299** MAPCHUNKSZ 4096 and MAPUNIT 1024 --> 4096 * 8 * 1024 = 32 Mb per chunk
300*/
301#define MAPCHUNKSZ 4096 /* #bytes per bitmap chunk (do not change) */
302
303#define SPCMINBLK 100 /* space threshold to give warning messages */
304#define SPCDFLINTVL 16 /* once every SPCDFLINTVL writes to cowfile, */
305 /* available space in filesystem is checked */
306
307#define CALCMAP(x) ((x)/(MAPCHUNKSZ*8))
308#define CALCBYTE(x) (((x)%(MAPCHUNKSZ*8))>>3)
309#define CALCBIT(x) ((x)&7)
310
311#define ALLCOW 1
312#define ALLRDO 2
313#define MIXEDUP 3
314
315static char allzeroes[MAPUNIT];
316
317/*
318** administration per cowdevice (pair of cowfile/rdofile)
319*/
320
321/* bit-values for state */
322#define COWDEVOPEN 0x01 /* cowdevice opened */
323#define COWRWCOWOPEN 0x02 /* cowfile opened read-write */
324#define COWRDCOWOPEN 0x04 /* cowfile opened read-only */
325#define COWWATCHDOG 0x08 /* ioctl for watchdog cowfile space active */
326
327#define COWCOWOPEN (COWRWCOWOPEN|COWRDCOWOPEN)
328
329struct cowloop_device
330{
331 /*
332 ** current status
333 */
334 int state; /* bit-values (see above) */
335 int opencnt; /* # opens for cowdevice */
336
337 /*
338 ** open file pointers
339 */
340 struct file *rdofp, *cowfp; /* open file pointers */
341 char *rdoname, *cowname; /* file names */
342
343 /*
344 ** request queue administration
345 */
346 struct request_queue *rqueue;
347 spinlock_t rqlock;
348 struct gendisk *gd;
349
350 /*
351 ** administration about read-only file
352 */
353 unsigned int numblocks; /* # blocks input file in MAPUNIT */
354 unsigned int blocksz; /* minimum unit to access this dev */
355 unsigned long fingerprint; /* fingerprint of current rdofile */
356 struct block_device *belowdev; /* block device below us */
357 struct gendisk *belowgd; /* gendisk for blk dev below us */
358 struct request_queue *belowq; /* req. queue of blk dev below us */
359
360 /*
361 ** bitmap administration to register which blocks are modified
362 */
363 long int mapsize; /* total size of bitmap (bytes) */
364 long int mapremain; /* remaining bytes in last bitmap */
365 int mapcount; /* number of bitmaps in use */
366 char **mapcache; /* area with pointers to bitmaps */
367
368 char *iobuf; /* databuffer of MAPUNIT bytes */
369 struct cowhead *cowhead; /* buffer containing cowhead */
370
371 /*
372 ** administration for interface with the kernel-thread
373 */
374 int pid; /* pid==0: no thread available */
375 struct request *req; /* request to be handled now */
376 wait_queue_head_t waitq; /* wait-Q: thread waits for work */
377 char closedown; /* boolean: thread exit required */
378 char qfilled; /* boolean: I/O request pending */
379 char iobusy; /* boolean: req under treatment */
380
381 /*
382 ** administration to keep track of free space in cowfile filesystem
383 */
384 unsigned long blksize; /* block size of fs (bytes) */
385 unsigned long blktotal; /* recent total space in fs (blocks) */
386 unsigned long blkavail; /* recent free space in fs (blocks) */
387
388 wait_queue_head_t watchq; /* wait-Q: watcher awaits threshold */
389 unsigned long watchthresh; /* threshold of watcher (blocks) */
390
391 /*
392 ** statistical counters
393 */
394 unsigned long rdoreads; /* number of read-actions rdo */
395 unsigned long cowreads; /* number of read-actions cow */
396 unsigned long cowwrites; /* number of write-actions */
397 unsigned long nrcowblocks; /* number of blocks in use on cow */
398};
399
400static struct cowloop_device **cowdevall; /* ptr to ptrs to all cowdevices */
401static struct semaphore cowdevlock; /* generic lock for cowdevs */
402
403static struct gendisk *cowctlgd; /* gendisk control channel */
404static spinlock_t cowctlrqlock; /* for req.q. of ctrl. channel */
405
406/*
407** private directory /proc/cow
408*/
409struct proc_dir_entry *cowlo_procdir;
410
411/*
412** function prototypes
413*/
414static long int cowlo_do_request (struct request *req);
415static void cowlo_sync (void);
416static int cowlo_checkio (struct cowloop_device *, int, loff_t);
417static int cowlo_readmix (struct cowloop_device *, void *, int, loff_t);
418static int cowlo_writemix (struct cowloop_device *, void *, int, loff_t);
419static long int cowlo_readrdo (struct cowloop_device *, void *, int, loff_t);
420static long int cowlo_readcow (struct cowloop_device *, void *, int, loff_t);
421static long int cowlo_readcowraw (struct cowloop_device *, void *, int, loff_t);
422static long int cowlo_writecow (struct cowloop_device *, void *, int, loff_t);
423static long int cowlo_writecowraw(struct cowloop_device *, void *, int, loff_t);
424
425#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,28))
426static int cowlo_ioctl (struct block_device *, fmode_t,
427 unsigned int, unsigned long);
428#else
429static int cowlo_ioctl (struct inode *, struct file *,
430 unsigned int, unsigned long);
431#endif
432
433static int cowlo_makepair (struct cowpair __user *);
434static int cowlo_removepair (unsigned long __user *);
435static int cowlo_watch (struct cowpair __user *);
436static int cowlo_cowctl (unsigned long __user *, int);
437static int cowlo_openpair (char *, char *, int, int);
438static int cowlo_closepair (struct cowloop_device *);
439static int cowlo_openrdo (struct cowloop_device *, char *);
440static int cowlo_opencow (struct cowloop_device *, char *, int);
441static void cowlo_undo_openrdo(struct cowloop_device *);
442static void cowlo_undo_opencow(struct cowloop_device *);
443
444/*****************************************************************************/
445/* System call handling */
446/*****************************************************************************/
447
448/*
449** handle system call open()/mount()
450**
451** returns:
452** 0 - okay
453** < 0 - error value
454*/
455static int
456#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,28))
457cowlo_open(struct block_device *bdev, fmode_t mode)
458#else
459cowlo_open(struct inode *inode, struct file *file)
460#endif
461{
462#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,28))
463 struct inode *inode = bdev->bd_inode;
464#endif
465 if (!inode)
466 return -EINVAL;
467
468 if (imajor(inode) != COWMAJOR) {
469 printk(KERN_WARNING
470 "cowloop - unexpected major %d\n", imajor(inode));
471 return -ENODEV;
472 }
473
474 switch (iminor(inode)) {
475 case COWCTL:
476 DEBUGP(DCOW"cowloop - open %d control\n", COWCTL);
477 break;
478
479 default:
480 DEBUGP(DCOW"cowloop - open minor %d\n", iminor(inode));
481
482 if ( iminor(inode) >= maxcows )
483 return -ENODEV;
484
485 if ( !((cowdevall[iminor(inode)])->state & COWDEVOPEN) )
486 return -ENODEV;
487
488 (cowdevall[iminor(inode)])->opencnt++;
489 }
490
491 return 0;
492}
493
494/*
495** handle system call close()/umount()
496**
497** returns:
498** 0 - okay
499*/
500static int
501#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,28))
502cowlo_release(struct gendisk *gd, fmode_t mode)
503#else
504cowlo_release(struct inode *inode, struct file *file)
505#endif
506{
507#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,28))
508 struct block_device *bdev;
509 struct inode *inode;
510
511 bdev = bdget_disk(gd, 0);
512 inode = bdev->bd_inode;
513#endif
514 if (!inode)
515 return 0;
516
517 DEBUGP(DCOW"cowloop - release (close) minor %d\n", iminor(inode));
518
519 if ( iminor(inode) != COWCTL)
520 (cowdevall[iminor(inode)])->opencnt--;
521
522 return 0;
523}
524
525/*
526** handle system call ioctl()
527**
528** returns:
529** 0 - okay
530** < 0 - error value
531*/
532static int
533#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,28))
534cowlo_ioctl(struct block_device *bdev, fmode_t mode,
535 unsigned int cmd, unsigned long arg)
536#else
537cowlo_ioctl(struct inode *inode, struct file *filp,
538 unsigned int cmd, unsigned long arg)
539#endif
540{
541 struct hd_geometry geo;
542#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,28))
543 struct inode *inode = bdev->bd_inode;
544#endif
545
546 DEBUGP(DCOW "cowloop - ioctl cmd %x\n", cmd);
547
548 switch ( iminor(inode) ) {
549
550 /*
551 ** allowed via control device only
552 */
553 case COWCTL:
554 switch (cmd) {
555 /*
556 ** write all bitmap chunks and cowheaders to cowfiles
557 */
558 case COWSYNC:
559 down(&cowdevlock);
560 cowlo_sync();
561 up(&cowdevlock);
562 return 0;
563
564 /*
565 ** open a new cowdevice (pair of rdofile/cowfile)
566 */
567 case COWMKPAIR:
568 return cowlo_makepair((void __user *)arg);
569
570 /*
571 ** close a cowdevice (pair of rdofile/cowfile)
572 */
573 case COWRMPAIR:
574 return cowlo_removepair((void __user *)arg);
575
576 /*
577 ** watch free space of filesystem containing cowfile
578 */
579 case COWWATCH:
580 return cowlo_watch((void __user *)arg);
581
582 /*
583 ** close cowfile for active device
584 */
585 case COWCLOSE:
586 return cowlo_cowctl((void __user *)arg, COWCLOSE);
587
588 /*
589 ** reopen cowfile read-only for active device
590 */
591 case COWRDOPEN:
592 return cowlo_cowctl((void __user *)arg, COWRDOPEN);
593
594 default:
595 return -EINVAL;
596 } /* end of switch on command */
597
598 /*
599 ** allowed for any other cowdevice
600 */
601 default:
602 switch (cmd) {
603 /*
604 ** HDIO_GETGEO must be supported for fdisk, etc
605 */
606 case HDIO_GETGEO:
607 geo.cylinders = 0;
608 geo.heads = 0;
609 geo.sectors = 0;
610
611 if (copy_to_user((void __user *)arg, &geo, sizeof geo))
612 return -EFAULT;
613 return 0;
614
615 default:
616 return -EINVAL;
617 } /* end of switch on ioctl-cmd code parameter */
618 } /* end of switch on minor number */
619}
620
621static struct block_device_operations cowlo_fops =
622{
623 .owner = THIS_MODULE,
624 .open = cowlo_open, /* called upon open */
625 .release = cowlo_release, /* called upon close */
626 .ioctl = cowlo_ioctl, /* called upon ioctl */
627};
628
629/*
630** handle ioctl-command COWMKPAIR:
631** open a new cowdevice (pair of rdofile/cowfile) on-the-fly
632**
633** returns:
634** 0 - okay
635** < 0 - error value
636*/
637static int
638cowlo_makepair(struct cowpair __user *arg)
639{
640 int i, rv=0;
641 struct cowpair cowpair;
642 unsigned char *cowpath;
643 unsigned char *rdopath;
644
645 /*
646 ** retrieve info about pathnames
647 */
648 if ( copy_from_user(&cowpair, arg, sizeof cowpair) )
649 return -EFAULT;
650
651 if ( (MAJOR(cowpair.device) != COWMAJOR) && (cowpair.device != ANYDEV) )
652 return -EINVAL;
653
654 if ( (MINOR(cowpair.device) >= maxcows) && (cowpair.device != ANYDEV) )
655 return -EINVAL;
656
657 /*
658 ** retrieve pathname strings
659 */
660 if ( (cowpair.cowflen > PATH_MAX) || (cowpair.rdoflen > PATH_MAX) )
661 return -ENAMETOOLONG;
662
663 if ( !(cowpath = kmalloc(cowpair.cowflen+1, GFP_KERNEL)) )
664 return -ENOMEM;
665
666 if ( copy_from_user(cowpath, (void __user *)cowpair.cowfile,
667 cowpair.cowflen) ) {
668 kfree(cowpath);
669 return -EFAULT;
670 }
671 *(cowpath+cowpair.cowflen) = 0;
672
673 if ( !(rdopath = kmalloc(cowpair.rdoflen+1, GFP_KERNEL)) ) {
674 kfree(cowpath);
675 return -ENOMEM;
676 }
677
678 if ( copy_from_user(rdopath, (void __user *)cowpair.rdofile,
679 cowpair.rdoflen) ) {
680 kfree(rdopath);
681 kfree(cowpath);
682 return -EFAULT;
683 }
684 *(rdopath+cowpair.rdoflen) = 0;
685
686 /*
687 ** open new cowdevice
688 */
689 if ( cowpair.device == ANYDEV) {
690 /*
691 ** search first unused minor
692 */
693 for (i=0, rv=-EBUSY; i < maxcows; i++) {
694 if ( !((cowdevall[i])->state & COWDEVOPEN) ) {
695 rv = cowlo_openpair(rdopath, cowpath, 0, i);
696 break;
697 }
698 }
699
700 if (rv) { /* open failed? */
701 kfree(rdopath);
702 kfree(cowpath);
703 return rv;
704 }
705
706 /*
707 ** return newly allocated cowdevice to user space
708 */
709 cowpair.device = MKDEV(COWMAJOR, i);
710
711 if ( copy_to_user(arg, &cowpair, sizeof cowpair)) {
712 kfree(rdopath);
713 kfree(cowpath);
714 return -EFAULT;
715 }
716 } else { /* specific minor requested */
717 if ( (rv = cowlo_openpair(rdopath, cowpath, 0,
718 MINOR(cowpair.device)))) {
719 kfree(rdopath);
720 kfree(cowpath);
721 return rv;
722 }
723 }
724
725 return 0;
726}
727
728/*
729** handle ioctl-command COWRMPAIR:
730** deactivate an existing cowdevice (pair of rdofile/cowfile) on-the-fly
731**
732** returns:
733** 0 - okay
734** < 0 - error value
735*/
736static int
737cowlo_removepair(unsigned long __user *arg)
738{
739 unsigned long cowdevice;
740 struct cowloop_device *cowdev;
741
742 /*
743 ** retrieve info about device to be removed
744 */
745 if ( copy_from_user(&cowdevice, arg, sizeof cowdevice))
746 return -EFAULT;
747
748 /*
749 ** verify major-minor number
750 */
751 if ( MAJOR(cowdevice) != COWMAJOR)
752 return -EINVAL;
753
754 if ( MINOR(cowdevice) >= maxcows)
755 return -EINVAL;
756
757 cowdev = cowdevall[MINOR(cowdevice)];
758
759 if ( !(cowdev->state & COWDEVOPEN) )
760 return -ENODEV;
761
762 /*
763 ** synchronize bitmaps and close cowdevice
764 */
765 if (cowdev->state & COWRWCOWOPEN) {
766 down(&cowdevlock);
767 cowlo_sync();
768 up(&cowdevlock);
769 }
770
771 return cowlo_closepair(cowdev);
772}
773
774/*
775** handle ioctl-command COWWATCH:
776** watch the free space of the filesystem containing a cowfile
777** of an open cowdevice
778**
779** returns:
780** 0 - okay
781** < 0 - error value
782*/
783static int
784cowlo_watch(struct cowpair __user *arg)
785{
786 struct cowloop_device *cowdev;
787 struct cowwatch cowwatch;
788
789 /*
790 ** retrieve structure holding info
791 */
792 if ( copy_from_user(&cowwatch, arg, sizeof cowwatch))
793 return -EFAULT;
794
795 /*
796 ** verify if cowdevice exists and is currently open
797 */
798 if ( MINOR(cowwatch.device) >= maxcows)
799 return -EINVAL;
800
801 cowdev = cowdevall[MINOR(cowwatch.device)];
802
803 if ( !(cowdev->state & COWDEVOPEN) )
804 return -ENODEV;
805
806 /*
807 ** if the WATCHWAIT-option is set, wait until the indicated
808 ** threshold is reached (only one waiter allowed)
809 */
810 if (cowwatch.flags & WATCHWAIT) {
811 /*
812 ** check if already another waiter active
813 ** for this cowdevice
814 */
815 if (cowdev->state & COWWATCHDOG)
816 return -EAGAIN;
817
818 cowdev->state |= COWWATCHDOG;
819
820 cowdev->watchthresh = (unsigned long long)
821 cowwatch.threshold /
822 (cowdev->blksize / 1024);
823
824 if (wait_event_interruptible(cowdev->watchq,
825 cowdev->watchthresh >= cowdev->blkavail)) {
826 cowdev->state &= ~COWWATCHDOG;
827 return EINTR;
828 }
829
830 cowdev->state &= ~COWWATCHDOG;
831 }
832
833 cowwatch.totalkb = (unsigned long long)cowdev->blktotal *
834 cowdev->blksize / 1024;
835 cowwatch.availkb = (unsigned long long)cowdev->blkavail *
836 cowdev->blksize / 1024;
837
838 if ( copy_to_user(arg, &cowwatch, sizeof cowwatch))
839 return -EFAULT;
840
841 return 0;
842}
843
844/*
845** handle ioctl-commands COWCLOSE and COWRDOPEN:
846** COWCLOSE - close the cowfile while the cowdevice remains open;
847** this allows an unmount of the filesystem on which
848** the cowfile resides
849** COWRDOPEN - close the cowfile and reopen it for read-only;
850** this allows a remount read-ony of the filesystem
851** on which the cowfile resides
852**
853** returns:
854** 0 - okay
855** < 0 - error value
856*/
857static int
858cowlo_cowctl(unsigned long __user *arg, int cmd)
859{
860 struct cowloop_device *cowdev;
861 unsigned long cowdevice;
862
863 /*
864 ** retrieve info about device to be removed
865 */
866 if ( copy_from_user(&cowdevice, arg, sizeof cowdevice))
867 return -EFAULT;
868
869 /*
870 ** verify major-minor number
871 */
872 if ( MAJOR(cowdevice) != COWMAJOR)
873 return -EINVAL;
874
875 if ( MINOR(cowdevice) >= maxcows)
876 return -EINVAL;
877
878 cowdev = cowdevall[MINOR(cowdevice)];
879
880 if ( !(cowdev->state & COWDEVOPEN) )
881 return -ENODEV;
882
883 /*
884 ** synchronize bitmaps and close cowfile
885 */
886 if (cowdev->state & COWRWCOWOPEN) {
887 down(&cowdevlock);
888 cowlo_sync();
889 up(&cowdevlock);
890 }
891
892 /*
893 ** handle specific ioctl-command
894 */
895 switch (cmd) {
896 case COWRDOPEN:
897 /*
898 ** if the cowfile is still opened read-write
899 */
900 if (cowdev->state & COWRWCOWOPEN) {
901 /*
902 ** close the cowfile
903 */
904 if (cowdev->cowfp)
905 filp_close(cowdev->cowfp, 0);
906
907 cowdev->state &= ~COWRWCOWOPEN;
908
909 /*
910 ** open again for read-only
911 */
912 cowdev->cowfp = filp_open(cowdev->cowname,
913 O_RDONLY|O_LARGEFILE, 0600);
914
915 if ( (cowdev->cowfp == NULL) || IS_ERR(cowdev->cowfp) ) {
916 printk(KERN_ERR
917 "cowloop - failed to reopen cowfile %s\n",
918 cowdev->cowname);
919 return -EINVAL;
920 }
921
922 /*
923 ** mark cowfile open for read-only
924 */
925 cowdev->state |= COWRDCOWOPEN;
926 } else {
927 return -EINVAL;
928 }
929 break;
930
931 case COWCLOSE:
932 /*
933 ** if the cowfile is still open
934 */
935 if (cowdev->state & COWCOWOPEN) {
936 /*
937 ** close the cowfile
938 */
939 if (cowdev->cowfp)
940 filp_close(cowdev->cowfp, 0);
941
942 cowdev->state &= ~COWCOWOPEN;
943 }
944 }
945
946 return 0;
947}
948
949
950/*****************************************************************************/
951/* Handling of I/O-requests for a cowdevice */
952/*****************************************************************************/
953
954/*
955** function to be called by core-kernel to handle the I/O-requests
956** in the queue
957*/
958static void
959#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,25))
960cowlo_request(struct request_queue *q)
961#else
962cowlo_request(request_queue_t *q)
963#endif
964{
965 struct request *req;
966 struct cowloop_device *cowdev;
967
968 DEBUGP(DCOW "cowloop - request function called....\n");
969
970 while((req = elv_next_request(q)) != NULL) {
971 DEBUGP(DCOW "cowloop - got next request\n");
972
973 if (! blk_fs_request(req)) {
974 /* this is not a normal file system request */
975 end_request(req, 0);
976 continue;
977 }
978 cowdev = req->rq_disk->private_data;
979
980 if (cowdev->iobusy)
981 return;
982 else
983 cowdev->iobusy = 1;
984
985 /*
986 ** when no kernel-thread is available, the request will
987 ** produce an I/O-error
988 */
989 if (!cowdev->pid) {
990 printk(KERN_ERR"cowloop - no thread available\n");
991 end_request(req, 0); /* request failed */
992 cowdev->iobusy = 0;
993 continue;
994 }
995
996 /*
997 ** handle I/O-request in the context of the kernel-thread
998 */
999 cowdev->req = req;
1000 cowdev->qfilled = 1;
1001
1002 wake_up_interruptible_sync(&cowdev->waitq);
1003
1004 /*
1005 ** get out of this function now while the I/O-request is
1006 ** under treatment of the kernel-thread; this function
1007 ** will be called again after the current I/O-request has
1008 ** been finished by the thread
1009 */
1010 return;
1011 }
1012}
1013
1014/*
1015** daemon-process (kernel-thread) executes this function
1016*/
1017static int
1018cowlo_daemon(struct cowloop_device *cowdev)
1019{
1020 int rv;
1021 int minor;
1022 char myname[16];
1023
1024 for (minor = 0; minor < maxcows; minor++) {
1025 if (cowdev == cowdevall[minor]) break;
1026 }
1027 sprintf(myname, "cowloopd%d", minor);
1028
1029 daemonize(myname);
1030
1031 while (!cowdev->closedown) {
1032 /*
1033 ** sleep while waiting for an I/O request;
1034 ** note that no non-interruptible wait has been used
1035 ** because the non-interruptible version of
1036 ** a *synchronous* wake_up does not exist (any more)
1037 */
1038 if (wait_event_interruptible(cowdev->waitq, cowdev->qfilled)){
1039 flush_signals(current); /* ignore signal-based wakeup */
1040 continue;
1041 }
1042
1043 if (cowdev->closedown) /* module will be unloaded ? */{
1044 cowdev->pid = 0;
1045 return 0;
1046 }
1047
1048 /*
1049 ** woken up by the I/O-request handler: treat requested I/O
1050 */
1051 cowdev->qfilled = 0;
1052
1053 rv = cowlo_do_request(cowdev->req);
1054
1055 /*
1056 ** reacquire the queue-spinlock for manipulating
1057 ** the request-queue and dequeue the request
1058 */
1059 spin_lock_irq(&cowdev->rqlock);
1060
1061 end_request(cowdev->req, rv);
1062 cowdev->iobusy = 0;
1063
1064 /*
1065 ** initiate the next request from the queue
1066 */
1067 cowlo_request(cowdev->rqueue);
1068
1069 spin_unlock_irq(&cowdev->rqlock);
1070 }
1071 return 0;
1072}
1073
1074/*
1075** function to be called in the context of the kernel thread
1076** to handle the queued I/O-requests
1077**
1078** returns:
1079** 0 - fail
1080** 1 - success
1081*/
1082static long int
1083cowlo_do_request(struct request *req)
1084{
1085 unsigned long len;
1086 long int rv;
1087 loff_t offset;
1088 struct cowloop_device *cowdev = req->rq_disk->private_data;
1089
1090 /*
1091 ** calculate some variables which are needed later on
1092 */
1093 len = req->current_nr_sectors << 9;
1094 offset = (loff_t) req->sector << 9;
1095
1096 DEBUGP(DCOW"cowloop - req cmd=%d offset=%lld len=%lu addr=%p\n",
1097 *(req->cmd), offset, len, req->buffer);
1098
1099 /*
1100 ** handle READ- or WRITE-request
1101 */
1102 switch (rq_data_dir(req)) {
1103 /**********************************************************/
1104 case READ:
1105 switch ( cowlo_checkio(cowdev, len, offset) ) {
1106 case ALLCOW:
1107 rv = cowlo_readcow(cowdev, req->buffer, len, offset);
1108 break;
1109
1110 case ALLRDO:
1111 rv = cowlo_readrdo(cowdev, req->buffer, len, offset);
1112 break;
1113
1114 case MIXEDUP:
1115 rv = cowlo_readmix(cowdev, req->buffer, len, offset);
1116 break;
1117
1118 default:
1119 rv = 0; /* never happens */
1120 }
1121 break;
1122
1123 /**********************************************************/
1124 case WRITE:
1125 switch ( cowlo_checkio(cowdev, len, offset) ) {
1126 case ALLCOW:
1127 /*
1128 ** straight-forward write will do...
1129 */
1130 DEBUGP(DCOW"cowloop - write straight ");
1131
1132 rv = cowlo_writecow(cowdev, req->buffer, len, offset);
1133 break; /* from switch */
1134
1135 case ALLRDO:
1136 if ( (len & MUMASK) == 0) {
1137 DEBUGP(DCOW"cowloop - write straight ");
1138
1139 rv = cowlo_writecow(cowdev, req->buffer,
1140 len, offset);
1141 break;
1142 }
1143
1144 case MIXEDUP:
1145 rv = cowlo_writemix(cowdev, req->buffer, len, offset);
1146 break;
1147
1148 default:
1149 rv = 0; /* never happens */
1150 }
1151 break;
1152
1153 default:
1154 printk(KERN_ERR
1155 "cowloop - unrecognized command %d\n", *(req->cmd));
1156 rv = 0;
1157 }
1158
1159 return (rv <= 0 ? 0 : 1);
1160}
1161
1162/*
1163** check for a given I/O-request if all underlying blocks
1164** (with size MAPUNIT) are either in the read-only file or in
1165** the cowfile (or a combination of the two)
1166**
1167** returns:
1168** ALLRDO - all underlying blocks in rdofile
1169** ALLCOW - all underlying blocks in cowfile
1170** MIXEDUP - underlying blocks partly in rdofile and partly in cowfile
1171*/
1172static int
1173cowlo_checkio(struct cowloop_device *cowdev, int len, loff_t offset)
1174{
1175 unsigned long mapnum, bytenum, bitnum, blocknr, partlen;
1176 long int totcnt, cowcnt;
1177 char *mc;
1178
1179 /*
1180 ** notice that the requested block might cross
1181 ** a blocksize boundary while one of the concerned
1182 ** blocks resides in the read-only file and another
1183 ** one in the copy-on-write file; in that case the
1184 ** request will be broken up into pieces
1185 */
1186 if ( (len <= MAPUNIT) &&
1187 (MAPUNIT - (offset & MUMASK) <= len) ) {
1188 /*
1189 ** easy situation:
1190 ** requested data-block entirely fits within
1191 ** the mapunit used for the bitmap
1192 ** check if that block is located in rdofile or
1193 ** cowfile
1194 */
1195 blocknr = offset >> MUSHIFT;
1196
1197 mapnum = CALCMAP (blocknr);
1198 bytenum = CALCBYTE(blocknr);
1199 bitnum = CALCBIT (blocknr);
1200
1201 if (*(*(cowdev->mapcache+mapnum)+bytenum)&(1<<bitnum))
1202 return ALLCOW;
1203 else
1204 return ALLRDO;
1205 }
1206
1207 /*
1208 ** less easy situation:
1209 ** the requested data-block does not fit within the mapunit
1210 ** used for the bitmap
1211 ** check if *all* underlying blocks involved reside on the rdofile
1212 ** or the cowfile (so still no breakup required)
1213 */
1214 for (cowcnt=totcnt=0; len > 0; len-=partlen, offset+=partlen, totcnt++){
1215 /*
1216 ** calculate blocknr of involved block
1217 */
1218 blocknr = offset >> MUSHIFT;
1219
1220 /*
1221 ** calculate partial length for this transfer
1222 */
1223 partlen = MAPUNIT - (offset & MUMASK);
1224 if (partlen > len)
1225 partlen = len;
1226
1227 /*
1228 ** is this block located in the cowfile
1229 */
1230 mapnum = CALCMAP (blocknr);
1231 bytenum = CALCBYTE(blocknr);
1232 bitnum = CALCBIT (blocknr);
1233
1234 mc = *(cowdev->mapcache+mapnum);
1235
1236 if (*(mc+bytenum)&(1<<bitnum))
1237 cowcnt++;;
1238
1239 DEBUGP(DCOW
1240 "cowloop - check %lu - map %lu, byte %lu, bit %lu, "
1241 "cowcnt %ld, totcnt %ld %02x %p\n",
1242 blocknr, mapnum, bytenum, bitnum, cowcnt, totcnt,
1243 *(mc+bytenum), mc);
1244 }
1245
1246 if (cowcnt == 0) /* all involved blocks on rdofile? */
1247 return ALLRDO;
1248
1249 if (cowcnt == totcnt) /* all involved blocks on cowfile? */
1250 return ALLCOW;
1251
1252 /*
1253 ** situation somewhat more complicated:
1254 ** involved underlying blocks spread over both files
1255 */
1256 return MIXEDUP;
1257}
1258
1259/*
1260** read requested chunk partly from rdofile and partly from cowfile
1261**
1262** returns:
1263** 0 - fail
1264** 1 - success
1265*/
1266static int
1267cowlo_readmix(struct cowloop_device *cowdev, void *buf, int len, loff_t offset)
1268{
1269 unsigned long mapnum, bytenum, bitnum, blocknr, partlen;
1270 long int rv;
1271 char *mc;
1272
1273 /*
1274 ** complicated approach: breakup required of read-request
1275 */
1276 for (rv=1; len > 0; len-=partlen, buf+=partlen, offset+=partlen) {
1277 /*
1278 ** calculate blocknr of entire block
1279 */
1280 blocknr = offset >> MUSHIFT;
1281
1282 /*
1283 ** calculate partial length for this transfer
1284 */
1285 partlen = MAPUNIT - (offset & MUMASK);
1286 if (partlen > len)
1287 partlen = len;
1288
1289 /*
1290 ** is this block located in the cowfile
1291 */
1292 mapnum = CALCMAP (blocknr);
1293 bytenum = CALCBYTE(blocknr);
1294 bitnum = CALCBIT (blocknr);
1295 mc = *(cowdev->mapcache+mapnum);
1296
1297 if (*(mc+bytenum)&(1<<bitnum)) {
1298 /*
1299 ** read (partial) block from cowfile
1300 */
1301 DEBUGP(DCOW"cowloop - split read "
1302 "cow partlen=%ld off=%lld\n", partlen, offset);
1303
1304 if (cowlo_readcow(cowdev, buf, partlen, offset) <= 0)
1305 rv = 0;
1306 } else {
1307 /*
1308 ** read (partial) block from rdofile
1309 */
1310 DEBUGP(DCOW"cowloop - split read "
1311 "rdo partlen=%ld off=%lld\n", partlen, offset);
1312
1313 if (cowlo_readrdo(cowdev, buf, partlen, offset) <= 0)
1314 rv = 0;
1315 }
1316 }
1317
1318 return rv;
1319}
1320
1321/*
1322** chunk to be written to the cowfile needs pieces to be
1323** read from the rdofile
1324**
1325** returns:
1326** 0 - fail
1327** 1 - success
1328*/
1329static int
1330cowlo_writemix(struct cowloop_device *cowdev, void *buf, int len, loff_t offset)
1331{
1332 unsigned long mapnum, bytenum, bitnum, blocknr, partlen;
1333 long int rv;
1334 char *mc;
1335
1336 /*
1337 ** somewhat more complicated stuff is required:
1338 ** if the request is larger than one underlying
1339 ** block or is spread over two underlying blocks,
1340 ** split the request into pieces; if a block does not
1341 ** start at a block boundary, take care that
1342 ** surrounding data is read first (if needed),
1343 ** fit the new data in and write it as a full block
1344 */
1345 for (rv=1; len > 0; len-=partlen, buf+=partlen, offset+=partlen) {
1346 /*
1347 ** calculate partial length for this transfer
1348 */
1349 partlen = MAPUNIT - (offset & MUMASK);
1350 if (partlen > len)
1351 partlen = len;
1352
1353 /*
1354 ** calculate blocknr of entire block
1355 */
1356 blocknr = offset >> MUSHIFT;
1357
1358 /*
1359 ** has this block been written before?
1360 */
1361 mapnum = CALCMAP (blocknr);
1362 bytenum = CALCBYTE(blocknr);
1363 bitnum = CALCBIT (blocknr);
1364 mc = *(cowdev->mapcache+mapnum);
1365
1366 if (*(mc+bytenum)&(1<<bitnum)) {
1367 /*
1368 ** block has been written before;
1369 ** write transparantly to cowfile
1370 */
1371 DEBUGP(DCOW
1372 "cowloop - splitwr transp\n");
1373
1374 if (cowlo_writecow(cowdev, buf, partlen, offset) <= 0)
1375 rv = 0;
1376 } else {
1377 /*
1378 ** block has never been written before,
1379 ** so read entire block from
1380 ** read-only file first, unless
1381 ** a full block is requested to
1382 ** be written
1383 */
1384 if (partlen < MAPUNIT) {
1385 if (cowlo_readrdo(cowdev, cowdev->iobuf,
1386 MAPUNIT, (loff_t)blocknr << MUSHIFT) <= 0)
1387 rv = 0;
1388 }
1389
1390 /*
1391 ** transfer modified part into
1392 ** the block just read
1393 */
1394 memcpy(cowdev->iobuf + (offset & MUMASK), buf, partlen);
1395
1396 /*
1397 ** write entire block to cowfile
1398 */
1399 DEBUGP(DCOW"cowloop - split "
1400 "partlen=%ld off=%lld\n",
1401 partlen, (loff_t)blocknr << MUSHIFT);
1402
1403 if (cowlo_writecow(cowdev, cowdev->iobuf, MAPUNIT,
1404 (loff_t)blocknr << MUSHIFT) <= 0)
1405 rv = 0;
1406 }
1407 }
1408
1409 return rv;
1410}
1411
1412/*****************************************************************************/
1413/* I/O-support for read-only file and copy-on-write file */
1414/*****************************************************************************/
1415
1416/*
1417** read data from the read-only file
1418**
1419** return-value: similar to user-mode read
1420*/
1421static long int
1422cowlo_readrdo(struct cowloop_device *cowdev, void *buf, int len, loff_t offset)
1423{
1424 long int rv;
1425 mm_segment_t old_fs;
1426 loff_t saveoffset = offset;
1427
1428 DEBUGP(DCOW"cowloop - readrdo called\n");
1429
1430 old_fs = get_fs();
1431 set_fs( get_ds() );
1432 rv = cowdev->rdofp->f_op->read(cowdev->rdofp, buf, len, &offset);
1433 set_fs(old_fs);
1434
1435 if (rv < len) {
1436 printk(KERN_WARNING "cowloop - read-failure %ld on rdofile"
1437 "- offset=%lld len=%d\n",
1438 rv, saveoffset, len);
1439 }
1440
1441 cowdev->rdoreads++;
1442 return rv;
1443}
1444
1445/*
1446** read cowfile from a modified offset, i.e. skipping the bitmap and cowhead
1447**
1448** return-value: similar to user-mode read
1449*/
1450static long int
1451cowlo_readcow(struct cowloop_device *cowdev, void *buf, int len, loff_t offset)
1452{
1453 DEBUGP(DCOW"cowloop - readcow called\n");
1454
1455 offset += cowdev->cowhead->doffset;
1456
1457 return cowlo_readcowraw(cowdev, buf, len, offset);
1458}
1459
1460/*
1461** read cowfile from an absolute offset
1462**
1463** return-value: similar to user-mode read
1464*/
1465static long int
1466cowlo_readcowraw(struct cowloop_device *cowdev,
1467 void *buf, int len, loff_t offset)
1468{
1469 long int rv;
1470 mm_segment_t old_fs;
1471 loff_t saveoffset = offset;
1472
1473 DEBUGP(DCOW"cowloop - readcowraw called\n");
1474
1475 /*
1476 ** be sure that cowfile is opened for read-write
1477 */
1478 if ( !(cowdev->state & COWCOWOPEN) ) {
1479 printk(KERN_WARNING
1480 "cowloop - read request from cowfile refused\n");
1481
1482 return -EBADF;
1483 }
1484
1485 /*
1486 ** issue low level read
1487 */
1488 old_fs = get_fs();
1489 set_fs( get_ds() );
1490 rv = cowdev->cowfp->f_op->read(cowdev->cowfp, buf, len, &offset);
1491 set_fs(old_fs);
1492
1493 if (rv < len) {
1494 printk(KERN_WARNING
1495 "cowloop - read-failure %ld on cowfile"
1496 "- offset=%lld len=%d\n", rv, saveoffset, len);
1497 }
1498
1499 cowdev->cowreads++;
1500 return rv;
1501}
1502
1503/*
1504** write cowfile from a modified offset, i.e. skipping the bitmap and cowhead
1505**
1506** if a block is written for the first time while its contents consists
1507** of binary zeroes only, the concerning bitmap is flushed to the cowfile
1508**
1509** return-value: similar to user-mode write
1510*/
1511static long int
1512cowlo_writecow(struct cowloop_device *cowdev, void *buf, int len, loff_t offset)
1513{
1514 long int rv;
1515 unsigned long mapnum=0, mapbyte=0, mapbit=0, cowblock=0, partlen;
1516 char *tmpptr, *mapptr = NULL;
1517 loff_t tmpoffset, mapoffset = 0;
1518
1519 DEBUGP(DCOW"cowloop - writecow called\n");
1520
1521 /*
1522 ** be sure that cowfile is opened for read-write
1523 */
1524 if ( !(cowdev->state & COWRWCOWOPEN) ) {
1525 printk(KERN_WARNING
1526 "cowloop - Write request to cowfile refused\n");
1527
1528 return -EBADF;
1529 }
1530
1531 /*
1532 ** write the entire block to the cowfile
1533 */
1534 tmpoffset = offset + cowdev->cowhead->doffset;
1535
1536 rv = cowlo_writecowraw(cowdev, buf, len, tmpoffset);
1537
1538 /*
1539 ** verify if enough space available on filesystem holding
1540 ** the cowfile
1541 ** - when the last write failed (might be caused by lack of space)
1542 ** - when a watcher is active (to react adequatly)
1543 ** - when the previous check indicated fs was almost full
1544 ** - with regular intervals
1545 */
1546 if ( (rv <= 0) ||
1547 (cowdev->state & COWWATCHDOG) ||
1548 (cowdev->blkavail / 2 < SPCDFLINTVL) ||
1549 (cowdev->cowwrites % SPCDFLINTVL == 0) ) {
1550 struct kstatfs ks;
1551
1552#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,18))
1553 if (vfs_statfs(cowdev->cowfp->f_dentry, &ks)==0){
1554#else
1555 if (vfs_statfs(cowdev->cowfp->f_dentry->d_inode->i_sb, &ks)==0){
1556#endif
1557 if (ks.f_bavail <= SPCMINBLK) {
1558 switch (ks.f_bavail) {
1559 case 0:
1560 case 1:
1561 case 2:
1562 case 3:
1563 printk(KERN_ALERT
1564 "cowloop - "
1565 "ALERT: cowfile full!\n");
1566 break;
1567
1568 default:
1569 printk(KERN_WARNING
1570 "cowloop - cowfile almost "
1571 "full (only %llu Kb free)\n",
1572 (unsigned long long)
1573 ks.f_bsize * ks.f_bavail /1024);
1574 }
1575 }
1576
1577 cowdev->blktotal = ks.f_blocks;
1578 cowdev->blkavail = ks.f_bavail;
1579
1580 /*
1581 ** wakeup watcher if threshold has been reached
1582 */
1583 if ( (cowdev->state & COWWATCHDOG) &&
1584 (cowdev->watchthresh >= cowdev->blkavail) ) {
1585 wake_up_interruptible(&cowdev->watchq);
1586 }
1587 }
1588 }
1589
1590 if (rv <= 0)
1591 return rv;
1592
1593 DEBUGP(DCOW"cowloop - block written\n");
1594
1595 /*
1596 ** check if block(s) is/are written to the cowfile
1597 ** for the first time; if so, adapt the bitmap
1598 */
1599 for (; len > 0; len-=partlen, offset+=partlen, buf+=partlen) {
1600 /*
1601 ** calculate partial length for this transfer
1602 */
1603 partlen = MAPUNIT - (offset & MUMASK);
1604 if (partlen > len)
1605 partlen = len;
1606
1607 /*
1608 ** calculate bitnr of written chunk of cowblock
1609 */
1610 cowblock = offset >> MUSHIFT;
1611
1612 mapnum = CALCMAP (cowblock);
1613 mapbyte = CALCBYTE(cowblock);
1614 mapbit = CALCBIT (cowblock);
1615
1616 if (*(*(cowdev->mapcache+mapnum)+mapbyte) & (1<<mapbit))
1617 continue; /* already written before */
1618
1619 /*
1620 ** if the block is written for the first time,
1621 ** the corresponding bit should be set in the bitmap
1622 */
1623 *(*(cowdev->mapcache+mapnum)+mapbyte) |= (1<<mapbit);
1624
1625 cowdev->nrcowblocks++;
1626
1627 DEBUGP(DCOW"cowloop - bitupdate blk=%ld map=%ld "
1628 "byte=%ld bit=%ld\n",
1629 cowblock, mapnum, mapbyte, mapbit);
1630
1631 /*
1632 ** check if the cowhead in the cowfile is currently
1633 ** marked clean; if so, mark it dirty and flush it
1634 */
1635 if ( !(cowdev->cowhead->flags &= COWDIRTY)) {
1636 cowdev->cowhead->flags |= COWDIRTY;
1637
1638 cowlo_writecowraw(cowdev, cowdev->cowhead,
1639 MAPUNIT, (loff_t)0);
1640 }
1641
1642 /*
1643 ** if the written datablock contained binary zeroes,
1644 ** the bitmap block should be marked to be flushed to disk
1645 ** (blocks containing all zeroes cannot be recovered by
1646 ** the cowrepair-program later on if cowloop is not properly
1647 ** removed via rmmod)
1648 */
1649 if ( memcmp(buf, allzeroes, partlen) ) /* not all zeroes? */
1650 continue; /* no flush needed */
1651
1652 /*
1653 ** calculate positions of bitmap block to be flushed
1654 ** - pointer of bitmap block in memory
1655 ** - offset of bitmap block in cowfile
1656 */
1657 tmpptr = *(cowdev->mapcache+mapnum) + (mapbyte & (~MUMASK));
1658 tmpoffset = (loff_t) MAPUNIT + mapnum * MAPCHUNKSZ +
1659 (mapbyte & (~MUMASK));
1660
1661 /*
1662 ** flush a bitmap block at the moment that all bits have
1663 ** been set in that block, i.e. at the moment that we
1664 ** switch to another bitmap block
1665 */
1666 if ( (mapoffset != 0) && (mapoffset != tmpoffset) ) {
1667 if (cowlo_writecowraw(cowdev, mapptr, MAPUNIT,
1668 mapoffset) < 0) {
1669 printk(KERN_WARNING
1670 "cowloop - write-failure on bitmap - "
1671 "blk=%ld map=%ld byte=%ld bit=%ld\n",
1672 cowblock, mapnum, mapbyte, mapbit);
1673 }
1674
1675 DEBUGP(DCOW"cowloop - bitmap blk written %lld\n",
1676 mapoffset);
1677 }
1678
1679 /*
1680 ** remember offset in cowfile and offset in memory
1681 ** for bitmap to be flushed; flushing will be done
1682 ** as soon as all updates in this bitmap block have
1683 ** been done
1684 */
1685 mapoffset = tmpoffset;
1686 mapptr = tmpptr;
1687 }
1688
1689 /*
1690 ** any new block written containing binary zeroes?
1691 */
1692 if (mapoffset) {
1693 if (cowlo_writecowraw(cowdev, mapptr, MAPUNIT, mapoffset) < 0) {
1694 printk(KERN_WARNING
1695 "cowloop - write-failure on bitmap - "
1696 "blk=%ld map=%ld byte=%ld bit=%ld\n",
1697 cowblock, mapnum, mapbyte, mapbit);
1698 }
1699
1700 DEBUGP(DCOW"cowloop - bitmap block written %lld\n", mapoffset);
1701 }
1702
1703 return rv;
1704}
1705
1706/*
1707** write cowfile from an absolute offset
1708**
1709** return-value: similar to user-mode write
1710*/
1711static long int
1712cowlo_writecowraw(struct cowloop_device *cowdev,
1713 void *buf, int len, loff_t offset)
1714{
1715 long int rv;
1716 mm_segment_t old_fs;
1717 loff_t saveoffset = offset;
1718
1719 DEBUGP(DCOW"cowloop - writecowraw called\n");
1720
1721 /*
1722 ** be sure that cowfile is opened for read-write
1723 */
1724 if ( !(cowdev->state & COWRWCOWOPEN) ) {
1725 printk(KERN_WARNING
1726 "cowloop - write request to cowfile refused\n");
1727
1728 return -EBADF;
1729 }
1730
1731 /*
1732 ** issue low level write
1733 */
1734 old_fs = get_fs();
1735 set_fs( get_ds() );
1736 rv = cowdev->cowfp->f_op->write(cowdev->cowfp, buf, len, &offset);
1737 set_fs(old_fs);
1738
1739 if (rv < len) {
1740 printk(KERN_WARNING
1741 "cowloop - write-failure %ld on cowfile"
1742 "- offset=%lld len=%d\n", rv, saveoffset, len);
1743 }
1744
1745 cowdev->cowwrites++;
1746 return rv;
1747}
1748
1749
1750/*
1751** readproc-function: called when the corresponding /proc-file is read
1752*/
1753static int
1754cowlo_readproc(char *buf, char **start, off_t pos, int cnt, int *eof, void *p)
1755{
1756 struct cowloop_device *cowdev = p;
1757
1758 revision[sizeof revision - 3] = '\0';
1759
1760 return sprintf(buf,
1761 " cowloop version: %9s\n\n"
1762 " device state: %s%s%s%s\n"
1763 " number of opens: %9d\n"
1764 " pid of thread: %9d\n\n"
1765 " read-only file: %9s\n"
1766 " rdoreads: %9lu\n\n"
1767 "copy-on-write file: %9s\n"
1768 " state cowfile: %9s\n"
1769 " bitmap-blocks: %9lu (of %d bytes)\n"
1770 " cowblocks in use: %9lu (of %d bytes)\n"
1771 " cowreads: %9lu\n"
1772 " cowwrites: %9lu\n",
1773 &revision[11],
1774
1775 cowdev->state & COWDEVOPEN ? "devopen " : "",
1776 cowdev->state & COWRWCOWOPEN ? "cowopenrw " : "",
1777 cowdev->state & COWRDCOWOPEN ? "cowopenro " : "",
1778 cowdev->state & COWWATCHDOG ? "watchdog " : "",
1779
1780 cowdev->opencnt,
1781 cowdev->pid,
1782 cowdev->rdoname,
1783 cowdev->rdoreads,
1784 cowdev->cowname,
1785 cowdev->cowhead->flags & COWDIRTY ? "dirty":"clean",
1786 cowdev->mapsize >> MUSHIFT, MAPUNIT,
1787 cowdev->nrcowblocks, MAPUNIT,
1788 cowdev->cowreads,
1789 cowdev->cowwrites);
1790}
1791
1792/*****************************************************************************/
1793/* Setup and destroy cowdevices */
1794/*****************************************************************************/
1795
1796/*
1797** open and prepare a cowdevice (rdofile and cowfile) and allocate bitmaps
1798**
1799** returns:
1800** 0 - okay
1801** < 0 - error value
1802*/
1803static int
1804cowlo_openpair(char *rdof, char *cowf, int autorecover, int minor)
1805{
1806 long int rv;
1807 struct cowloop_device *cowdev = cowdevall[minor];
1808 struct kstatfs ks;
1809
1810 down(&cowdevlock);
1811
1812 /*
1813 ** requested device exists?
1814 */
1815 if (minor >= maxcows) {
1816 up(&cowdevlock);
1817 return -ENODEV;
1818 }
1819
1820 /*
1821 ** requested device already assigned to cowdevice?
1822 */
1823 if (cowdev->state & COWDEVOPEN) {
1824 up(&cowdevlock);
1825 return -EBUSY;
1826 }
1827
1828 /*
1829 ** initialize administration
1830 */
1831 memset(cowdev, 0, sizeof *cowdev);
1832
1833 spin_lock_init (&cowdev->rqlock);
1834 init_waitqueue_head(&cowdev->waitq);
1835 init_waitqueue_head(&cowdev->watchq);
1836
1837 /*
1838 ** open the read-only file
1839 */
1840 DEBUGP(DCOW"cowloop - call openrdo....\n");
1841
1842 if ( (rv = cowlo_openrdo(cowdev, rdof)) ) {
1843 cowlo_undo_openrdo(cowdev);
1844 up(&cowdevlock);
1845 return rv;
1846 }
1847
1848 /*
1849 ** open the cowfile
1850 */
1851 DEBUGP(DCOW"cowloop - call opencow....\n");
1852
1853 if ( (rv = cowlo_opencow(cowdev, cowf, autorecover)) ) {
1854 cowlo_undo_openrdo(cowdev);
1855 cowlo_undo_opencow(cowdev);
1856 up(&cowdevlock);
1857 return rv;
1858 }
1859
1860 /*
1861 ** administer total and available size of filesystem holding cowfile
1862 */
1863#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,18))
1864 if (vfs_statfs(cowdev->cowfp->f_dentry, &ks)==0){
1865#else
1866 if (vfs_statfs(cowdev->cowfp->f_dentry->d_inode->i_sb, &ks)==0){
1867#endif
1868 cowdev->blksize = ks.f_bsize;
1869 cowdev->blktotal = ks.f_blocks;
1870 cowdev->blkavail = ks.f_bavail;
1871 } else {
1872 cowdev->blksize = 1024; /* avoid division by zero */
1873 }
1874
1875 /*
1876 ** flush the (recovered) bitmaps and cowhead to the cowfile
1877 */
1878 DEBUGP(DCOW"cowloop - call cowsync....\n");
1879
1880 cowlo_sync();
1881
1882 /*
1883 ** allocate gendisk for the cow device
1884 */
1885 DEBUGP(DCOW"cowloop - alloc disk....\n");
1886
1887 if ((cowdev->gd = alloc_disk(1)) == NULL) {
1888 printk(KERN_WARNING
1889 "cowloop - unable to alloc_disk for cowloop\n");
1890
1891 cowlo_undo_openrdo(cowdev);
1892 cowlo_undo_opencow(cowdev);
1893 up(&cowdevlock);
1894 return -ENOMEM;
1895 }
1896
1897 cowdev->gd->major = COWMAJOR;
1898 cowdev->gd->first_minor = minor;
1899 cowdev->gd->minors = 1;
1900 cowdev->gd->fops = &cowlo_fops;
1901 cowdev->gd->private_data = cowdev;
1902 sprintf(cowdev->gd->disk_name, "%s%d", DEVICE_NAME, minor);
1903
1904 /* in .5 Kb units */
1905 set_capacity(cowdev->gd, (cowdev->numblocks*(MAPUNIT/512)));
1906
1907 DEBUGP(DCOW"cowloop - init request queue....\n");
1908
1909 if ((cowdev->rqueue = blk_init_queue(cowlo_request, &cowdev->rqlock))
1910 == NULL) {
1911 printk(KERN_WARNING
1912 "cowloop - unable to get request queue for cowloop\n");
1913
1914 del_gendisk(cowdev->gd);
1915 cowlo_undo_openrdo(cowdev);
1916 cowlo_undo_opencow(cowdev);
1917 up(&cowdevlock);
1918 return -EINVAL;
1919 }
1920
1921 blk_queue_hardsect_size(cowdev->rqueue, cowdev->blocksz);
1922 cowdev->gd->queue = cowdev->rqueue;
1923
1924 /*
1925 ** start kernel thread to handle requests
1926 */
1927 DEBUGP(DCOW"cowloop - kickoff daemon....\n");
1928
1929 cowdev->pid = kernel_thread((int (*)(void *))cowlo_daemon, cowdev, 0);
1930
1931 /*
1932 ** create a file below directory /proc/cow for this new cowdevice
1933 */
1934 if (cowlo_procdir) {
1935 char tmpname[64];
1936
1937 sprintf(tmpname, "%d", minor);
1938
1939 create_proc_read_entry(tmpname, 0 , cowlo_procdir,
1940 cowlo_readproc, cowdev);
1941 }
1942
1943 cowdev->state |= COWDEVOPEN;
1944
1945 cowdev->rdoname = rdof;
1946 cowdev->cowname = cowf;
1947
1948 /*
1949 ** enable the new disk; this triggers the first request!
1950 */
1951 DEBUGP(DCOW"cowloop - call add_disk....\n");
1952
1953 add_disk(cowdev->gd);
1954
1955 up(&cowdevlock);
1956 return 0;
1957}
1958
1959/*
1960** close a cowdevice (pair of rdofile/cowfile) and release memory
1961**
1962** returns:
1963** 0 - okay
1964** < 0 - error value
1965*/
1966static int
1967cowlo_closepair(struct cowloop_device *cowdev)
1968{
1969 int minor;
1970
1971 down(&cowdevlock);
1972
1973 /*
1974 ** if cowdevice is not activated at all, refuse
1975 */
1976 if ( !(cowdev->state & COWDEVOPEN) ) {
1977 up(&cowdevlock);
1978 return -ENODEV;
1979 }
1980
1981 /*
1982 ** if this cowdevice is still open, refuse
1983 */
1984 if (cowdev->opencnt > 0) {
1985 up(&cowdevlock);
1986 return -EBUSY;
1987 }
1988
1989 up(&cowdevlock);
1990
1991 /*
1992 ** wakeup watcher (if any)
1993 */
1994 if (cowdev->state & COWWATCHDOG) {
1995 cowdev->watchthresh = cowdev->blkavail;
1996 wake_up_interruptible(&cowdev->watchq);
1997 }
1998
1999 /*
2000 ** wakeup kernel-thread to be able to exit
2001 ** and wait until it has exited
2002 */
2003 cowdev->closedown = 1;
2004 cowdev->qfilled = 1;
2005 wake_up_interruptible(&cowdev->waitq);
2006
2007 while (cowdev->pid)
2008 schedule();
2009
2010 del_gendisk(cowdev->gd); /* revert the alloc_disk() */
2011 put_disk(cowdev->gd); /* revert the add_disk() */
2012
2013 if (cowlo_procdir) {
2014 char tmpname[64];
2015
2016 for (minor = 0; minor < maxcows; minor++) {
2017 if (cowdev == cowdevall[minor]) break;
2018 }
2019 sprintf(tmpname, "%d", minor);
2020
2021 remove_proc_entry(tmpname, cowlo_procdir);
2022 }
2023
2024 blk_cleanup_queue(cowdev->rqueue);
2025
2026 /*
2027 ** release memory for filenames if these names have
2028 ** been allocated dynamically
2029 */
2030 if ( (cowdev->cowname) && (cowdev->cowname != cowfile))
2031 kfree(cowdev->cowname);
2032
2033 if ( (cowdev->rdoname) && (cowdev->rdoname != rdofile))
2034 kfree(cowdev->rdoname);
2035
2036 cowlo_undo_openrdo(cowdev);
2037 cowlo_undo_opencow(cowdev);
2038
2039 cowdev->state &= ~COWDEVOPEN;
2040
2041 return 0;
2042}
2043
2044/*
2045** open the read-only file
2046**
2047** returns:
2048** 0 - okay
2049** < 0 - error value
2050*/
2051static int
2052cowlo_openrdo(struct cowloop_device *cowdev, char *rdof)
2053{
2054 struct file *f;
2055 struct inode *inode;
2056 long int i, nrval;
2057
2058 DEBUGP(DCOW"cowloop - openrdo called\n");
2059
2060 /*
2061 ** open the read-only file
2062 */
2063 if(*rdof == '\0') {
2064 printk(KERN_ERR
2065 "cowloop - specify name for read-only file\n\n");
2066 return -EINVAL;
2067 }
2068
2069 f = filp_open(rdof, O_RDONLY|O_LARGEFILE, 0);
2070
2071 if ( (f == NULL) || IS_ERR(f) ) {
2072 printk(KERN_ERR
2073 "cowloop - open of rdofile %s failed\n", rdof);
2074 return -EINVAL;
2075 }
2076
2077 cowdev->rdofp = f;
2078
2079 inode = f->f_dentry->d_inode;
2080
2081 if ( !S_ISREG(inode->i_mode) && !S_ISBLK(inode->i_mode) ) {
2082 printk(KERN_ERR
2083 "cowloop - %s not regular file or blockdev\n", rdof);
2084 return -EINVAL;
2085 }
2086
2087 DEBUGP(DCOW"cowloop - determine size rdo....\n");
2088
2089 /*
2090 ** determine block-size and total size of read-only file
2091 */
2092 if (S_ISREG(inode->i_mode)) {
2093 /*
2094 ** read-only file is a regular file
2095 */
2096 cowdev->blocksz = 512; /* other value fails */
2097 cowdev->numblocks = inode->i_size >> MUSHIFT;
2098
2099 if (inode->i_size & MUMASK) {
2100 printk(KERN_WARNING
2101 "cowloop - rdofile %s truncated to multiple "
2102 "of %d bytes\n", rdof, MAPUNIT);
2103 }
2104
2105 DEBUGP(DCOW"cowloop - RO=regular: numblocks=%d, blocksz=%d\n",
2106 cowdev->numblocks, cowdev->blocksz);
2107 } else {
2108 /*
2109 ** read-only file is a block device
2110 */
2111 cowdev->belowdev = inode->i_bdev;
2112 cowdev->belowgd = cowdev->belowdev->bd_disk; /* gendisk */
2113
2114 if (cowdev->belowdev->bd_part) {
2115 cowdev->numblocks = cowdev->belowdev->bd_part->nr_sects
2116 / (MAPUNIT/512);
2117 }
2118
2119 if (cowdev->belowgd) {
2120 cowdev->belowq = cowdev->belowgd->queue;
2121
2122 if (cowdev->numblocks == 0) {
2123#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,27))
2124 cowdev->numblocks = get_capacity(cowdev->belowgd)
2125 / (MAPUNIT/512);
2126#else
2127 cowdev->numblocks = cowdev->belowgd->capacity
2128 / (MAPUNIT/512);
2129#endif
2130 }
2131 }
2132
2133
2134 if (cowdev->belowq)
2135 cowdev->blocksz = cowdev->belowq->hardsect_size;
2136
2137 if (cowdev->blocksz == 0)
2138 cowdev->blocksz = BLOCK_SIZE; /* default 2^10 */
2139
2140 DEBUGP(DCOW"cowloop - numblocks=%d, "
2141 "blocksz=%d, belowgd=%p, belowq=%p\n",
2142 cowdev->numblocks, cowdev->blocksz,
2143 cowdev->belowgd, cowdev->belowq);
2144
2145 DEBUGP(DCOW"cowloop - belowdev.bd_block_size=%d\n",
2146 cowdev->belowdev->bd_block_size);
2147 }
2148
2149 if (cowdev->numblocks == 0) {
2150 printk(KERN_ERR "cowloop - %s has no contents\n", rdof);
2151 return -EINVAL;
2152 }
2153
2154 /*
2155 ** reserve space in memory as generic I/O buffer
2156 */
2157 cowdev->iobuf = kmalloc(MAPUNIT, GFP_KERNEL);
2158
2159 if (!cowdev->iobuf) {
2160 printk(KERN_ERR
2161 "cowloop - cannot get space for buffer %d\n", MAPUNIT);
2162 return -ENOMEM;
2163 }
2164
2165 DEBUGP(DCOW"cowloop - determine fingerprint rdo....\n");
2166
2167 /*
2168 ** determine fingerprint for read-only file
2169 ** calculate fingerprint from first four datablocks
2170 ** which do not contain binary zeroes
2171 */
2172 for (i=0, cowdev->fingerprint=0, nrval=0;
2173 (nrval < 4)&&(i < cowdev->numblocks); i++) {
2174 int j;
2175 unsigned char cs;
2176
2177 /*
2178 ** read next block
2179 */
2180 if (cowlo_readrdo(cowdev, cowdev->iobuf, MAPUNIT,
2181 (loff_t)i << MUSHIFT) < 1)
2182 break;
2183
2184 /*
2185 ** calculate fingerprint by adding all byte-values
2186 */
2187 for (j=0, cs=0; j < MAPUNIT; j++)
2188 cs += *(cowdev->iobuf+j);
2189
2190 if (cs == 0) /* block probably contained zeroes */
2191 continue;
2192
2193 /*
2194 ** shift byte-value to proper place in final fingerprint
2195 */
2196 cowdev->fingerprint |= cs << (nrval*8);
2197 nrval++;
2198 }
2199
2200 return 0;
2201}
2202
2203/*
2204** undo memory allocs and file opens issued so far
2205** related to the read-only file
2206*/
2207static void
2208cowlo_undo_openrdo(struct cowloop_device *cowdev)
2209{
2210 if(cowdev->iobuf);
2211 kfree(cowdev->iobuf);
2212
2213 if (cowdev->rdofp)
2214 filp_close(cowdev->rdofp, 0);
2215}
2216
2217/*
2218** open the cowfile
2219**
2220** returns:
2221** 0 - okay
2222** < 0 - error value
2223*/
2224static int
2225cowlo_opencow(struct cowloop_device *cowdev, char *cowf, int autorecover)
2226{
2227 long int i, rv;
2228 int minor;
2229 unsigned long nb;
2230 struct file *f;
2231 struct inode *inode;
2232 loff_t offset;
2233 struct cowloop_device *cowtmp;
2234
2235 DEBUGP(DCOW"cowloop - opencow called\n");
2236
2237 /*
2238 ** open copy-on-write file (read-write)
2239 */
2240 if (cowf[0] == '\0') {
2241 printk(KERN_ERR
2242 "cowloop - specify name of copy-on-write file\n\n");
2243 return -EINVAL;
2244 }
2245
2246 f = filp_open(cowf, O_RDWR|O_LARGEFILE, 0600);
2247
2248 if ( (f == NULL) || IS_ERR(f) ) {
2249 /*
2250 ** non-existing cowfile: try to create
2251 */
2252 f = filp_open(cowf, O_RDWR|O_CREAT|O_LARGEFILE, 0600);
2253
2254 if ( (f == NULL) || IS_ERR(f) ) {
2255 printk(KERN_ERR
2256 "cowloop - failed to open file %s for read-write\n\n",
2257 cowf);
2258 return -EINVAL;
2259 }
2260 }
2261
2262 cowdev->cowfp = f;
2263
2264 inode = f->f_dentry->d_inode;
2265
2266 if (!S_ISREG(inode->i_mode)) {
2267 printk(KERN_ERR "cowloop - %s is not regular file\n", cowf);
2268 return -EINVAL;
2269 }
2270
2271 /*
2272 ** check if this cowfile is already in use for another cowdevice
2273 */
2274 for (minor = 0; minor < maxcows; minor++) {
2275
2276 cowtmp = cowdevall[minor];
2277
2278 if ( !(cowtmp->state & COWDEVOPEN) )
2279 continue;
2280
2281 if (cowtmp == cowdev)
2282 continue;
2283
2284 if (cowtmp->cowfp->f_dentry->d_inode == f->f_dentry->d_inode) {
2285 printk(KERN_ERR
2286 "cowloop - %s: already in use as cow\n", cowf);
2287 return -EBUSY;
2288 }
2289 }
2290
2291 /*
2292 ** mark cowfile open for read-write
2293 */
2294 cowdev->state |= COWRWCOWOPEN;
2295
2296 /*
2297 ** calculate size (in bytes) for total bitmap in cowfile;
2298 ** when the size of the cowhead block is added, the start-offset
2299 ** for the modified data blocks can be found
2300 */
2301 nb = cowdev->numblocks;
2302
2303 if (nb%8) /* transform #bits to #bytes */
2304 nb+=8; /* rounded if necessary */
2305 nb /= 8;
2306
2307 if (nb & MUMASK) /* round up #bytes to MAPUNIT chunks */
2308 cowdev->mapsize = ( (nb>>MUSHIFT) +1) << MUSHIFT;
2309 else
2310 cowdev->mapsize = nb;
2311
2312 /*
2313 ** reserve space in memory for the cowhead
2314 */
2315 cowdev->cowhead = kmalloc(MAPUNIT, GFP_KERNEL);
2316
2317 if (!cowdev->cowhead) {
2318 printk(KERN_ERR "cowloop - cannot get space for cowhead %d\n",
2319 MAPUNIT);
2320 return -ENOMEM;
2321 }
2322
2323 memset(cowdev->cowhead, 0, MAPUNIT);
2324
2325 DEBUGP(DCOW"cowloop - prepare cowhead....\n");
2326
2327 /*
2328 ** check if the cowfile exists or should be created
2329 */
2330 if (inode->i_size != 0) {
2331 /*
2332 ** existing cowfile: read the cow head
2333 */
2334 if (inode->i_size < MAPUNIT) {
2335 printk(KERN_ERR
2336 "cowloop - existing cowfile %s too small\n",
2337 cowf);
2338 return -EINVAL;
2339 }
2340
2341 cowlo_readcowraw(cowdev, cowdev->cowhead, MAPUNIT, (loff_t) 0);
2342
2343 /*
2344 ** verify if the existing file is really a cowfile
2345 */
2346 if (cowdev->cowhead->magic != COWMAGIC) {
2347 printk(KERN_ERR
2348 "cowloop - cowfile %s has incorrect format\n",
2349 cowf);
2350 return -EINVAL;
2351 }
2352
2353 /*
2354 ** verify the cowhead version of the cowfile
2355 */
2356 if (cowdev->cowhead->version > COWVERSION) {
2357 printk(KERN_ERR
2358 "cowloop - cowfile %s newer than this driver\n",
2359 cowf);
2360 return -EINVAL;
2361 }
2362
2363 /*
2364 ** make sure that this is not a packed cowfile
2365 */
2366 if (cowdev->cowhead->flags & COWPACKED) {
2367 printk(KERN_ERR
2368 "cowloop - packed cowfile %s not accepted\n", cowf);
2369 return -EINVAL;
2370 }
2371
2372 /*
2373 ** verify if the cowfile has been properly closed
2374 */
2375 if (cowdev->cowhead->flags & COWDIRTY) {
2376 /*
2377 ** cowfile was not properly closed;
2378 ** check if automatic recovery is required
2379 ** (actual recovery will be done later on)
2380 */
2381 if (!autorecover) {
2382 printk(KERN_ERR
2383 "cowloop - cowfile %s is dirty "
2384 "(not properly closed by rmmod?)\n",
2385 cowf);
2386 printk(KERN_ERR
2387 "cowloop - run cowrepair or specify "
2388 "'option=r' to recover\n");
2389 return -EINVAL;
2390 }
2391 }
2392
2393 /*
2394 ** verify if the cowfile is really related to this rdofile
2395 */
2396 if (cowdev->cowhead->rdoblocks != cowdev->numblocks) {
2397 printk(KERN_ERR
2398 "cowloop - cowfile %s (size %lld) not related "
2399 "to rdofile (size %lld)\n",
2400 cowf,
2401 (long long)cowdev->cowhead->rdoblocks <<MUSHIFT,
2402 (long long)cowdev->numblocks <<MUSHIFT);
2403 return -EINVAL;
2404 }
2405
2406 if (cowdev->cowhead->rdofingerprint != cowdev->fingerprint) {
2407 printk(KERN_ERR
2408 "cowloop - cowfile %s not related to rdofile "
2409 " (fingerprint err - rdofile modified?)\n", cowf);
2410 return -EINVAL;
2411 }
2412 } else {
2413 /*
2414 ** new cowfile: determine the minimal size (cowhead+bitmap)
2415 */
2416 offset = (loff_t) MAPUNIT + cowdev->mapsize - 1;
2417
2418 if ( cowlo_writecowraw(cowdev, "", 1, offset) < 1) {
2419 printk(KERN_ERR
2420 "cowloop - cannot set cowfile to size %lld\n",
2421 offset+1);
2422 return -EINVAL;
2423 }
2424
2425 /*
2426 ** prepare new cowhead
2427 */
2428 cowdev->cowhead->magic = COWMAGIC;
2429 cowdev->cowhead->version = COWVERSION;
2430 cowdev->cowhead->mapunit = MAPUNIT;
2431 cowdev->cowhead->mapsize = cowdev->mapsize;
2432 cowdev->cowhead->rdoblocks = cowdev->numblocks;
2433 cowdev->cowhead->rdofingerprint = cowdev->fingerprint;
2434 cowdev->cowhead->cowused = 0;
2435
2436 /*
2437 ** calculate start offset of data in cowfile,
2438 ** rounded up to multiple of 4K to avoid
2439 ** unnecessary disk-usage for written datablocks in
2440 ** the sparsed cowfile on e.g. 4K filesystems
2441 */
2442 cowdev->cowhead->doffset =
2443 ((MAPUNIT+cowdev->mapsize+4095)>>12)<<12;
2444 }
2445
2446 cowdev->cowhead->flags = 0;
2447
2448 DEBUGP(DCOW"cowloop - reserve space bitmap....\n");
2449
2450 /*
2451 ** reserve space in memory for the entire bitmap and
2452 ** fill it with the bitmap-data from disk; the entire
2453 ** bitmap is allocated in several chunks because kmalloc
2454 ** has restrictions regarding the allowed size per kmalloc
2455 */
2456 cowdev->mapcount = (cowdev->mapsize+MAPCHUNKSZ-1)/MAPCHUNKSZ;
2457
2458 /*
2459 ** the size of every bitmap chunk will be MAPCHUNKSZ bytes, except for
2460 ** the last bitmap chunk: calculate remaining size for this chunk
2461 */
2462 if (cowdev->mapsize % MAPCHUNKSZ == 0)
2463 cowdev->mapremain = MAPCHUNKSZ;
2464 else
2465 cowdev->mapremain = cowdev->mapsize % MAPCHUNKSZ;
2466
2467 /*
2468 ** allocate space to store all pointers for the bitmap-chunks
2469 ** (initialize area with zeroes to allow proper undo)
2470 */
2471 cowdev->mapcache = kmalloc(cowdev->mapcount * sizeof(char *),
2472 GFP_KERNEL);
2473 if (!cowdev->mapcache) {
2474 printk(KERN_ERR
2475 "cowloop - can not allocate space for bitmap ptrs\n");
2476 return -ENOMEM;
2477 }
2478
2479 memset(cowdev->mapcache, 0, cowdev->mapcount * sizeof(char *));
2480
2481 /*
2482 ** allocate space to store the bitmap-chunks themselves
2483 */
2484 for (i=0; i < cowdev->mapcount; i++) {
2485 if (i < (cowdev->mapcount-1))
2486 *(cowdev->mapcache+i) = kmalloc(MAPCHUNKSZ, GFP_KERNEL);
2487 else
2488 *(cowdev->mapcache+i) = kmalloc(cowdev->mapremain,
2489 GFP_KERNEL);
2490
2491 if (*(cowdev->mapcache+i) == NULL) {
2492 printk(KERN_ERR "cowloop - no space for bitmapchunk %ld"
2493 " totmapsz=%ld, mapcnt=%d mapunit=%d\n",
2494 i, cowdev->mapsize, cowdev->mapcount,
2495 MAPUNIT);
2496 return -ENOMEM;
2497 }
2498 }
2499
2500 DEBUGP(DCOW"cowloop - read bitmap from cow....\n");
2501
2502 /*
2503 ** read the entire bitmap from the cowfile into the in-memory cache;
2504 ** count the number of blocks that are in use already
2505 ** (statistical purposes)
2506 */
2507 for (i=0, offset=MAPUNIT; i < cowdev->mapcount;
2508 i++, offset+=MAPCHUNKSZ) {
2509 unsigned long numbytes;
2510
2511 if (i < (cowdev->mapcount-1))
2512 /*
2513 ** full bitmap chunk
2514 */
2515 numbytes = MAPCHUNKSZ;
2516 else
2517 /*
2518 ** last bitmap chunk: might be partly filled
2519 */
2520 numbytes = cowdev->mapremain;
2521
2522 cowlo_readcowraw(cowdev, *(cowdev->mapcache+i),
2523 numbytes, offset);
2524 }
2525
2526 /*
2527 ** if the cowfile was dirty and automatic recovery is required,
2528 ** reconstruct a proper bitmap in memory now
2529 */
2530 if (cowdev->cowhead->flags & COWDIRTY) {
2531 unsigned long long blocknum;
2532 char databuf[MAPUNIT];
2533 unsigned long mapnum, mapbyte, mapbit;
2534
2535 printk(KERN_NOTICE "cowloop - recover dirty cowfile %s....\n",
2536 cowf);
2537
2538 /*
2539 ** read all data blocks
2540 */
2541 for (blocknum=0, rv=1, offset=0;
2542 cowlo_readcow(cowdev, databuf, MAPUNIT, offset) > 0;
2543 blocknum++, offset += MAPUNIT) {
2544
2545 /*
2546 ** if this datablock contains real data (not binary
2547 ** zeroes), set the corresponding bit in the bitmap
2548 */
2549 if ( memcmp(databuf, allzeroes, MAPUNIT) == 0)
2550 continue;
2551
2552 mapnum = CALCMAP (blocknum);
2553 mapbyte = CALCBYTE(blocknum);
2554 mapbit = CALCBIT (blocknum);
2555
2556 *(*(cowdev->mapcache+mapnum)+mapbyte) |= (1<<mapbit);
2557 }
2558
2559 printk(KERN_NOTICE "cowloop - cowfile recovery completed\n");
2560 }
2561
2562 /*
2563 ** count all bits set in the bitmaps for statistical purposes
2564 */
2565 for (i=0, cowdev->nrcowblocks = 0; i < cowdev->mapcount; i++) {
2566 long numbytes;
2567 char *p;
2568
2569 if (i < (cowdev->mapcount-1))
2570 numbytes = MAPCHUNKSZ;
2571 else
2572 numbytes = cowdev->mapremain;
2573
2574 p = *(cowdev->mapcache+i);
2575
2576 for (numbytes--; numbytes >= 0; numbytes--, p++) {
2577 /*
2578 ** for only eight checks the following construction
2579 ** is faster than a loop-construction
2580 */
2581 if ((*p) & 0x01) cowdev->nrcowblocks++;
2582 if ((*p) & 0x02) cowdev->nrcowblocks++;
2583 if ((*p) & 0x04) cowdev->nrcowblocks++;
2584 if ((*p) & 0x08) cowdev->nrcowblocks++;
2585 if ((*p) & 0x10) cowdev->nrcowblocks++;
2586 if ((*p) & 0x20) cowdev->nrcowblocks++;
2587 if ((*p) & 0x40) cowdev->nrcowblocks++;
2588 if ((*p) & 0x80) cowdev->nrcowblocks++;
2589 }
2590 }
2591
2592 /*
2593 ** consistency-check for number of bits set in bitmap
2594 */
2595 if ( !(cowdev->cowhead->flags & COWDIRTY) &&
2596 (cowdev->cowhead->cowused != cowdev->nrcowblocks) ) {
2597 printk(KERN_ERR "cowloop - inconsistent cowfile admi\n");
2598 return -EINVAL;
2599 }
2600
2601 return 0;
2602}
2603
2604/*
2605** undo memory allocs and file opens issued so far
2606** related to the cowfile
2607*/
2608static void
2609cowlo_undo_opencow(struct cowloop_device *cowdev)
2610{
2611 int i;
2612
2613 if (cowdev->mapcache) {
2614 for (i=0; i < cowdev->mapcount; i++) {
2615 if (*(cowdev->mapcache+i) != NULL)
2616 kfree( *(cowdev->mapcache+i) );
2617 }
2618
2619 kfree(cowdev->mapcache);
2620 }
2621
2622 if (cowdev->cowhead)
2623 kfree(cowdev->cowhead);
2624
2625 if ( (cowdev->state & COWCOWOPEN) && (cowdev->cowfp) )
2626 filp_close(cowdev->cowfp, 0);
2627
2628 /*
2629 ** mark cowfile closed
2630 */
2631 cowdev->state &= ~COWCOWOPEN;
2632}
2633
2634/*
2635** flush the entire bitmap and the cowhead (clean) to the cowfile
2636**
2637** must be called with the cowdevices-lock set
2638*/
2639static void
2640cowlo_sync(void)
2641{
2642 int i, minor;
2643 loff_t offset;
2644 struct cowloop_device *cowdev;
2645
2646 for (minor=0; minor < maxcows; minor++) {
2647 cowdev = cowdevall[minor];
2648 if ( ! (cowdev->state & COWRWCOWOPEN) )
2649 continue;
2650
2651 for (i=0, offset=MAPUNIT; i < cowdev->mapcount;
2652 i++, offset += MAPCHUNKSZ) {
2653 unsigned long numbytes;
2654
2655 if (i < (cowdev->mapcount-1))
2656 /*
2657 ** full bitmap chunk
2658 */
2659 numbytes = MAPCHUNKSZ;
2660 else
2661 /*
2662 ** last bitmap chunk: might be partly filled
2663 */
2664 numbytes = cowdev->mapremain;
2665
2666 DEBUGP(DCOW
2667 "cowloop - flushing bitmap %2d (%3ld Kb)\n",
2668 i, numbytes/1024);
2669
2670 if (cowlo_writecowraw(cowdev, *(cowdev->mapcache+i),
2671 numbytes, offset) < numbytes) {
2672 break;
2673 }
2674 }
2675
2676 /*
2677 ** flush clean up-to-date cowhead to cowfile
2678 */
2679 cowdev->cowhead->cowused = cowdev->nrcowblocks;
2680 cowdev->cowhead->flags &= ~COWDIRTY;
2681
2682 DEBUGP(DCOW "cowloop - flushing cowhead (%3d Kb)\n",
2683 MAPUNIT/1024);
2684
2685 cowlo_writecowraw(cowdev, cowdev->cowhead, MAPUNIT, (loff_t) 0);
2686 }
2687}
2688
2689/*****************************************************************************/
2690/* Module loading/unloading */
2691/*****************************************************************************/
2692
2693/*
2694** called during insmod/modprobe
2695*/
2696static int __init
2697cowlo_init_module(void)
2698{
2699 int rv;
2700 int minor, uptocows;
2701
2702 revision[sizeof revision - 3] = '\0';
2703
2704 printk(KERN_NOTICE "cowloop - (C) 2009 ATComputing.nl - version: %s\n", &revision[11]);
2705 printk(KERN_NOTICE "cowloop - info: www.ATComputing.nl/cowloop\n");
2706
2707 memset(allzeroes, 0, MAPUNIT);
2708
2709 /*
2710 ** Setup administration for all possible cowdevices.
2711 ** Note that their minor numbers go from 0 to MAXCOWS-1 inclusive
2712 ** and minor == MAXCOWS-1 is reserved for the control device.
2713 */
2714 if ((maxcows < 1) || (maxcows > MAXCOWS)) {
2715 printk(KERN_WARNING
2716 "cowloop - maxcows exceeds maximum of %d\n", MAXCOWS);
2717
2718 maxcows = DFLCOWS;
2719 }
2720
2721 /* allocate room for a table with a pointer to each cowloop_device: */
2722 if ( (cowdevall = kmalloc(maxcows * sizeof(struct cowloop_device *),
2723 GFP_KERNEL)) == NULL) {
2724 printk(KERN_WARNING
2725 "cowloop - can not alloc table for %d devs\n", maxcows);
2726 uptocows = 0;
2727 rv = -ENOMEM;
2728 goto error_out;
2729 }
2730 memset(cowdevall, 0, maxcows * sizeof(struct cowloop_device *));
2731 /* then hook an actual cowloop_device struct to each pointer: */
2732 for (minor=0; minor < maxcows; minor++) {
2733 if ((cowdevall[minor] = kmalloc(sizeof(struct cowloop_device),
2734 GFP_KERNEL)) == NULL) {
2735 printk(KERN_WARNING
2736 "cowloop - can not alloc admin-struct for dev no %d\n", minor);
2737
2738 uptocows = minor; /* this is how far we got.... */
2739 rv = -ENOMEM;
2740 goto error_out;
2741 }
2742 memset(cowdevall[minor], 0, sizeof(struct cowloop_device));
2743 }
2744 uptocows = maxcows; /* we got all devices */
2745
2746 sema_init(&cowdevlock, 1);
2747
2748 /*
2749 ** register cowloop module
2750 */
2751 if ( register_blkdev(COWMAJOR, DEVICE_NAME) < 0) {
2752 printk(KERN_WARNING
2753 "cowloop - unable to get major %d for cowloop\n", COWMAJOR);
2754 rv = -EIO;
2755 goto error_out;
2756 }
2757
2758 /*
2759 ** create a directory below /proc to allocate a file
2760 ** for each cowdevice that is allocated later on
2761 */
2762 cowlo_procdir = proc_mkdir("cow", NULL);
2763
2764 /*
2765 ** check if a cowdevice has to be opened during insmod/modprobe;
2766 ** two parameters should be specified then: rdofile= and cowfile=
2767 */
2768 if( (rdofile[0] != '\0') && (cowfile[0] != '\0') ) {
2769 char *po = option;
2770 int wantrecover = 0;
2771
2772 /*
2773 ** check if automatic recovery is wanted
2774 */
2775 while (*po) {
2776 if (*po == 'r') {
2777 wantrecover = 1;
2778 break;
2779 }
2780 po++;
2781 }
2782
2783 /*
2784 ** open new cowdevice with minor number 0
2785 */
2786 if ( (rv = cowlo_openpair(rdofile, cowfile, wantrecover, 0))) {
2787 remove_proc_entry("cow", NULL);
2788 unregister_blkdev(COWMAJOR, DEVICE_NAME);
2789 goto error_out;
2790 }
2791 } else {
2792 /*
2793 ** check if only one parameter has been specified
2794 */
2795 if( (rdofile[0] != '\0') || (cowfile[0] != '\0') ) {
2796 printk(KERN_ERR
2797 "cowloop - only one filename specified\n");
2798 remove_proc_entry("cow", NULL);
2799 unregister_blkdev(COWMAJOR, DEVICE_NAME);
2800 rv = -EINVAL;
2801 goto error_out;
2802 }
2803 }
2804
2805 /*
2806 ** allocate fake disk as control channel to handle the requests
2807 ** to activate and deactivate cowdevices dynamically
2808 */
2809 if (!(cowctlgd = alloc_disk(1))) {
2810 printk(KERN_WARNING
2811 "cowloop - unable to alloc_disk for cowctl\n");
2812
2813 remove_proc_entry("cow", NULL);
2814 (void) cowlo_closepair(cowdevall[0]);
2815 unregister_blkdev(COWMAJOR, DEVICE_NAME);
2816 rv = -ENOMEM;
2817 goto error_out;
2818 }
2819
2820 spin_lock_init(&cowctlrqlock);
2821 cowctlgd->major = COWMAJOR;
2822 cowctlgd->first_minor = COWCTL;
2823 cowctlgd->minors = 1;
2824 cowctlgd->fops = &cowlo_fops;
2825 cowctlgd->private_data = NULL;
2826 /* the device has capacity 0, so there will be no q-requests */
2827 cowctlgd->queue = blk_init_queue(NULL, &cowctlrqlock);
2828 sprintf(cowctlgd->disk_name, "cowctl");
2829 set_capacity(cowctlgd, 0);
2830
2831 add_disk(cowctlgd);
2832
2833 printk(KERN_NOTICE "cowloop - number of configured cowdevices: %d\n",
2834 maxcows);
2835 if (rdofile[0] != '\0') {
2836 printk(KERN_NOTICE "cowloop - initialized on rdofile=%s\n",
2837 rdofile);
2838 } else {
2839 printk(KERN_NOTICE "cowloop - initialized without rdofile yet\n");
2840 }
2841 return 0;
2842
2843error_out:
2844 for (minor=0; minor < uptocows ; minor++) {
2845 kfree(cowdevall[minor]);
2846 }
2847 kfree(cowdevall);
2848 return rv;
2849}
2850
2851/*
2852** called during rmmod
2853*/
2854static void __exit
2855cowlo_cleanup_module(void)
2856{
2857 int minor;
2858
2859 /*
2860 ** flush bitmaps and cowheads to the cowfiles
2861 */
2862 down(&cowdevlock);
2863 cowlo_sync();
2864 up(&cowdevlock);
2865
2866 /*
2867 ** close all cowdevices
2868 */
2869 for (minor=0; minor < maxcows; minor++)
2870 (void) cowlo_closepair(cowdevall[minor]);
2871
2872#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,23))
2873 unregister_blkdev(COWMAJOR, DEVICE_NAME);
2874#else
2875 if (unregister_blkdev(COWMAJOR, DEVICE_NAME) != 0)
2876 printk(KERN_WARNING "cowloop - cannot unregister blkdev\n");
2877#endif
2878
2879 /*
2880 ** get rid of /proc/cow and unregister the driver
2881 */
2882 remove_proc_entry("cow", NULL);
2883
2884 for (minor = 0; minor < maxcows; minor++) {
2885 kfree(cowdevall[minor]);
2886 }
2887 kfree(cowdevall);
2888
2889 del_gendisk(cowctlgd); /* revert the alloc_disk() */
2890 put_disk (cowctlgd); /* revert the add_disk() */
2891 blk_cleanup_queue(cowctlgd->queue); /* cleanup the empty queue */
2892
2893 printk(KERN_NOTICE "cowloop - unloaded\n");
2894}
2895
2896module_init(cowlo_init_module);
2897module_exit(cowlo_cleanup_module);
diff --git a/drivers/staging/cowloop/cowloop.h b/drivers/staging/cowloop/cowloop.h
new file mode 100644
index 000000000000..bbd4a35ac667
--- /dev/null
+++ b/drivers/staging/cowloop/cowloop.h
@@ -0,0 +1,66 @@
1/*
2** DO NOT MODIFY THESE VALUES (would make old cowfiles unusable)
3*/
4#define MAPUNIT 1024 /* blocksize for bit in bitmap */
5#define MUSHIFT 10 /* bitshift for bit in bitmap */
6#define MUMASK 0x3ff /* bitmask for bit in bitmap */
7
8#define COWMAGIC 0x574f437f /* byte-swapped '7f C O W' */
9#define COWDIRTY 0x01
10#define COWPACKED 0x02
11#define COWVERSION 1
12
13struct cowhead
14{
15 int magic; /* identifies a cowfile */
16 short version; /* version of cowhead */
17 short flags; /* flags indicating status */
18 unsigned long mapunit; /* blocksize per bit in bitmap */
19 unsigned long mapsize; /* total size of bitmap (bytes) */
20 unsigned long doffset; /* start-offset datablocks in cow */
21 unsigned long rdoblocks; /* size of related read-only file */
22 unsigned long rdofingerprint; /* fingerprint of read-only file */
23 unsigned long cowused; /* number of datablocks used in cow */
24};
25
26#define COWDEVDIR "/dev/cow/"
27#define COWDEVICE COWDEVDIR "%ld"
28#define COWCONTROL COWDEVDIR "ctl"
29
30#define MAXCOWS 1024
31#define COWCTL (MAXCOWS-1) /* minor number of /dev/cow/ctl */
32
33#define COWPROCDIR "/proc/cow/"
34#define COWPROCFILE COWPROCDIR "%d"
35
36/*
37** ioctl related stuff
38*/
39#define ANYDEV ((unsigned long)-1)
40
41struct cowpair
42{
43 unsigned char *rdofile; /* pathname of the rdofile */
44 unsigned char *cowfile; /* pathname of the cowfile */
45 unsigned short rdoflen; /* length of rdofile pathname */
46 unsigned short cowflen; /* length of cowfile pathname */
47 unsigned long device; /* requested/returned device number */
48};
49
50struct cowwatch
51{
52 int flags; /* request flags */
53 unsigned long device; /* requested device number */
54 unsigned long threshold; /* continue if free Kb < threshold */
55 unsigned long totalkb; /* ret: total filesystem size (Kb) */
56 unsigned long availkb; /* ret: free filesystem size (Kb) */
57};
58
59#define WATCHWAIT 0x01 /* block until threshold reached */
60
61#define COWSYNC _IO ('C', 1)
62#define COWMKPAIR _IOW ('C', 2, struct cowpair)
63#define COWRMPAIR _IOW ('C', 3, unsigned long)
64#define COWWATCH _IOW ('C', 4, struct cowwatch)
65#define COWCLOSE _IOW ('C', 5, unsigned long)
66#define COWRDOPEN _IOW ('C', 6, unsigned long)