aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRichard Cochran <richardcochran@gmail.com>2010-06-14 12:10:33 -0400
committerDavid Woodhouse <David.Woodhouse@intel.com>2010-08-02 04:03:41 -0400
commit9938424f0c4d208883cbf32083ec2bfcc220f85b (patch)
treee4f7581c7543673fe63c98f9804e934a77aeb7ef
parent1df620637fc3b252b69c92ced486b5b6b643dd1a (diff)
mtd: add an ioctl to query the lock status of a flash sector
This patchs adds a way for user space programs to find out whether a flash sector is locked. An optional driver method in the mtd_info struct provides the information. Signed-off-by: Richard Cochran <richard.cochran@omicron.at> Signed-off-by: Artem Bityutskiy <Artem.Bityutskiy@nokia.com> Signed-off-by: David Woodhouse <David.Woodhouse@intel.com>
-rw-r--r--drivers/mtd/chips/cfi_cmdset_0001.c10
-rw-r--r--drivers/mtd/mtdchar.c14
-rw-r--r--drivers/mtd/mtdpart.c10
-rw-r--r--include/linux/mtd/mtd.h1
-rw-r--r--include/mtd/mtd-abi.h1
5 files changed, 36 insertions, 0 deletions
diff --git a/drivers/mtd/chips/cfi_cmdset_0001.c b/drivers/mtd/chips/cfi_cmdset_0001.c
index 62f3ea9de848..2fadb0239ba3 100644
--- a/drivers/mtd/chips/cfi_cmdset_0001.c
+++ b/drivers/mtd/chips/cfi_cmdset_0001.c
@@ -63,6 +63,8 @@ static int cfi_intelext_erase_varsize(struct mtd_info *, struct erase_info *);
63static void cfi_intelext_sync (struct mtd_info *); 63static void cfi_intelext_sync (struct mtd_info *);
64static int cfi_intelext_lock(struct mtd_info *mtd, loff_t ofs, uint64_t len); 64static int cfi_intelext_lock(struct mtd_info *mtd, loff_t ofs, uint64_t len);
65static int cfi_intelext_unlock(struct mtd_info *mtd, loff_t ofs, uint64_t len); 65static int cfi_intelext_unlock(struct mtd_info *mtd, loff_t ofs, uint64_t len);
66static int cfi_intelext_is_locked(struct mtd_info *mtd, loff_t ofs,
67 uint64_t len);
66#ifdef CONFIG_MTD_OTP 68#ifdef CONFIG_MTD_OTP
67static int cfi_intelext_read_fact_prot_reg (struct mtd_info *, loff_t, size_t, size_t *, u_char *); 69static int cfi_intelext_read_fact_prot_reg (struct mtd_info *, loff_t, size_t, size_t *, u_char *);
68static int cfi_intelext_read_user_prot_reg (struct mtd_info *, loff_t, size_t, size_t *, u_char *); 70static int cfi_intelext_read_user_prot_reg (struct mtd_info *, loff_t, size_t, size_t *, u_char *);
@@ -448,6 +450,7 @@ struct mtd_info *cfi_cmdset_0001(struct map_info *map, int primary)
448 mtd->sync = cfi_intelext_sync; 450 mtd->sync = cfi_intelext_sync;
449 mtd->lock = cfi_intelext_lock; 451 mtd->lock = cfi_intelext_lock;
450 mtd->unlock = cfi_intelext_unlock; 452 mtd->unlock = cfi_intelext_unlock;
453 mtd->is_locked = cfi_intelext_is_locked;
451 mtd->suspend = cfi_intelext_suspend; 454 mtd->suspend = cfi_intelext_suspend;
452 mtd->resume = cfi_intelext_resume; 455 mtd->resume = cfi_intelext_resume;
453 mtd->flags = MTD_CAP_NORFLASH; 456 mtd->flags = MTD_CAP_NORFLASH;
@@ -2139,6 +2142,13 @@ static int cfi_intelext_unlock(struct mtd_info *mtd, loff_t ofs, uint64_t len)
2139 return ret; 2142 return ret;
2140} 2143}
2141 2144
2145static int cfi_intelext_is_locked(struct mtd_info *mtd, loff_t ofs,
2146 uint64_t len)
2147{
2148 return cfi_varsize_frob(mtd, do_getlockstatus_oneblock,
2149 ofs, len, NULL) ? 1 : 0;
2150}
2151
2142#ifdef CONFIG_MTD_OTP 2152#ifdef CONFIG_MTD_OTP
2143 2153
2144typedef int (*otp_op_t)(struct map_info *map, struct flchip *chip, 2154typedef int (*otp_op_t)(struct map_info *map, struct flchip *chip,
diff --git a/drivers/mtd/mtdchar.c b/drivers/mtd/mtdchar.c
index 8b223c0343ee..a8e69dd2b2e4 100644
--- a/drivers/mtd/mtdchar.c
+++ b/drivers/mtd/mtdchar.c
@@ -676,6 +676,20 @@ static int mtd_ioctl(struct inode *inode, struct file *file,
676 break; 676 break;
677 } 677 }
678 678
679 case MEMISLOCKED:
680 {
681 struct erase_info_user einfo;
682
683 if (copy_from_user(&einfo, argp, sizeof(einfo)))
684 return -EFAULT;
685
686 if (!mtd->is_locked)
687 ret = -EOPNOTSUPP;
688 else
689 ret = mtd->is_locked(mtd, einfo.start, einfo.length);
690 break;
691 }
692
679 /* Legacy interface */ 693 /* Legacy interface */
680 case MEMGETOOBSEL: 694 case MEMGETOOBSEL:
681 { 695 {
diff --git a/drivers/mtd/mtdpart.c b/drivers/mtd/mtdpart.c
index b8043a9ba32d..4c539ded0b70 100644
--- a/drivers/mtd/mtdpart.c
+++ b/drivers/mtd/mtdpart.c
@@ -264,6 +264,14 @@ static int part_unlock(struct mtd_info *mtd, loff_t ofs, uint64_t len)
264 return part->master->unlock(part->master, ofs + part->offset, len); 264 return part->master->unlock(part->master, ofs + part->offset, len);
265} 265}
266 266
267static int part_is_locked(struct mtd_info *mtd, loff_t ofs, uint64_t len)
268{
269 struct mtd_part *part = PART(mtd);
270 if ((len + ofs) > mtd->size)
271 return -EINVAL;
272 return part->master->is_locked(part->master, ofs + part->offset, len);
273}
274
267static void part_sync(struct mtd_info *mtd) 275static void part_sync(struct mtd_info *mtd)
268{ 276{
269 struct mtd_part *part = PART(mtd); 277 struct mtd_part *part = PART(mtd);
@@ -402,6 +410,8 @@ static struct mtd_part *add_one_partition(struct mtd_info *master,
402 slave->mtd.lock = part_lock; 410 slave->mtd.lock = part_lock;
403 if (master->unlock) 411 if (master->unlock)
404 slave->mtd.unlock = part_unlock; 412 slave->mtd.unlock = part_unlock;
413 if (master->is_locked)
414 slave->mtd.is_locked = part_is_locked;
405 if (master->block_isbad) 415 if (master->block_isbad)
406 slave->mtd.block_isbad = part_block_isbad; 416 slave->mtd.block_isbad = part_block_isbad;
407 if (master->block_markbad) 417 if (master->block_markbad)
diff --git a/include/linux/mtd/mtd.h b/include/linux/mtd/mtd.h
index 5326435a7571..43b7d72c6116 100644
--- a/include/linux/mtd/mtd.h
+++ b/include/linux/mtd/mtd.h
@@ -216,6 +216,7 @@ struct mtd_info {
216 /* Chip-supported device locking */ 216 /* Chip-supported device locking */
217 int (*lock) (struct mtd_info *mtd, loff_t ofs, uint64_t len); 217 int (*lock) (struct mtd_info *mtd, loff_t ofs, uint64_t len);
218 int (*unlock) (struct mtd_info *mtd, loff_t ofs, uint64_t len); 218 int (*unlock) (struct mtd_info *mtd, loff_t ofs, uint64_t len);
219 int (*is_locked) (struct mtd_info *mtd, loff_t ofs, uint64_t len);
219 220
220 /* Power Management functions */ 221 /* Power Management functions */
221 int (*suspend) (struct mtd_info *mtd); 222 int (*suspend) (struct mtd_info *mtd);
diff --git a/include/mtd/mtd-abi.h b/include/mtd/mtd-abi.h
index be51ae2bd0ff..e12872e3c694 100644
--- a/include/mtd/mtd-abi.h
+++ b/include/mtd/mtd-abi.h
@@ -110,6 +110,7 @@ struct otp_info {
110#define MEMERASE64 _IOW('M', 20, struct erase_info_user64) 110#define MEMERASE64 _IOW('M', 20, struct erase_info_user64)
111#define MEMWRITEOOB64 _IOWR('M', 21, struct mtd_oob_buf64) 111#define MEMWRITEOOB64 _IOWR('M', 21, struct mtd_oob_buf64)
112#define MEMREADOOB64 _IOWR('M', 22, struct mtd_oob_buf64) 112#define MEMREADOOB64 _IOWR('M', 22, struct mtd_oob_buf64)
113#define MEMISLOCKED _IOR('M', 23, struct erase_info_user)
113 114
114/* 115/*
115 * Obsolete legacy interface. Keep it in order not to break userspace 116 * Obsolete legacy interface. Keep it in order not to break userspace