Hello community,
here is the log from the commit of package mmc-utils for openSUSE:Factory checked in at 2016-07-01 10:00:40
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/mmc-utils (Old)
and /work/SRC/openSUSE:Factory/.mmc-utils.new (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "mmc-utils"
Changes:
--------
--- /work/SRC/openSUSE:Factory/mmc-utils/mmc-utils.changes 2016-05-17 17:15:22.000000000 +0200
+++ /work/SRC/openSUSE:Factory/.mmc-utils.new/mmc-utils.changes 2016-07-01 10:00:42.000000000 +0200
@@ -1,0 +2,7 @@
+Wed Jun 29 15:19:02 UTC 2016 - mpluskal@suse.com
+
+- Update to version 0.1+git.20160623:
+ * mmc-utils: Add ability to configure write protect on an eMMC device
+ * mmc-utils: Add Command Queue fields to Extended CSD
+
+-------------------------------------------------------------------
Old:
----
mmc-utils-0.1+git.20160511.tar.xz
New:
----
mmc-utils-0.1+git.20160623.tar.xz
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ mmc-utils.spec ++++++
--- /var/tmp/diff_new_pack.ST2CKr/_old 2016-07-01 10:00:43.000000000 +0200
+++ /var/tmp/diff_new_pack.ST2CKr/_new 2016-07-01 10:00:43.000000000 +0200
@@ -17,7 +17,7 @@
Name: mmc-utils
-Version: 0.1+git.20160511
+Version: 0.1+git.20160623
Release: 0
Summary: Tools for MMC/SD devices
License: GPL-2.0
@@ -27,9 +27,6 @@
Source1: https://www.gnu.org/licenses/gpl-2.0.txt
Patch0: do_not_use_asm_generic.patch
BuildRequires: xz
-# switch from versioning based only on date of last git commit
-Provides: %{name} = 20151118
-Obsoletes: %{name} = 20151118
BuildRoot: %{_tmppath}/%{name}-%{version}-build
%description
++++++ _service ++++++
--- /var/tmp/diff_new_pack.ST2CKr/_old 2016-07-01 10:00:43.000000000 +0200
+++ /var/tmp/diff_new_pack.ST2CKr/_new 2016-07-01 10:00:43.000000000 +0200
@@ -1,14 +1,14 @@
<services>
- <service mode="localonly" name="tar_scm">
+ <service mode="disabled" name="tar_scm">
<param name="url">git://git.kernel.org/pub/scm/linux/kernel/git/cjb/mmc-utils.git</param>
<param name="scm">git</param>
<param name="filename">mmc-utils</param>
<param name="changesgenerate">enable</param>
<param name="versionformat">0.1+git.%cd</param>
</service>
- <service mode="localonly" name="recompress">
+ <service mode="disabled" name="recompress">
<param name="file">*.tar</param>
<param name="compression">xz</param>
</service>
- <service mode="localonly" name="set_version"/>
+ <service mode="disabled" name="set_version"/>
</services>
++++++ mmc-utils-0.1+git.20160511.tar.xz -> mmc-utils-0.1+git.20160623.tar.xz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/mmc-utils-0.1+git.20160511/mmc.c new/mmc-utils-0.1+git.20160623/mmc.c
--- old/mmc-utils-0.1+git.20160511/mmc.c 2016-05-12 22:45:28.000000000 +0200
+++ new/mmc-utils-0.1+git.20160623/mmc.c 2016-06-29 17:19:02.000000000 +0200
@@ -58,14 +58,28 @@
"Print extcsd data from <device>.",
NULL
},
- { do_writeprotect_get, -1,
- "writeprotect get", "<device>\n"
- "Determine the eMMC writeprotect status of <device>.",
+ { do_writeprotect_boot_get, -1,
+ "writeprotect boot get", "<device>\n"
+ "Print the boot partitions write protect status for <device>.",
NULL
},
- { do_writeprotect_set, -1,
- "writeprotect set", "<device>\n"
- "Set the eMMC writeprotect status of <device>.\nThis sets the eMMC to be write-protected until next boot.",
+ { do_writeprotect_boot_set, -1,
+ "writeprotect boot set", "<device>\n"
+ "Set the boot partitions write protect status for <device>.\nThis sets the eMMC boot partitions to be write-protected until\nthe next boot.",
+ NULL
+ },
+ { do_writeprotect_user_set, -4,
+ "writeprotect user set", "<type>" "<start block>" "<blocks>" "<device>\n"
+#ifdef DANGEROUS_COMMANDS_ENABLED
+ "Set the write protect configuration for the specified region\nof the user area for <device>.\n<type> must be \"none|temp|pwron|perm\".\n \"none\" - Clear temporary write protection.\n \"temp\" - Set temporary write protection.\n \"pwron\" - Set write protection until the next poweron.\n \"perm\" - Set permanent write protection.\n<start block> specifies the first block of the protected area.\n<blocks> specifies the size of the protected area in blocks.\nNOTE! The area must start and end on Write Protect Group\nboundries, Use the \"writeprotect user get\" command to get the\nWrite Protect Group size.\nNOTE! \"perm\" is a one-time programmable (unreversible) change.",
+#else
+ "Set the write protect configuration for the specified region\nof the user area for <device>.\n<type> must be \"none|temp|pwron\".\n \"none\" - Clear temporary write protection.\n \"temp\" - Set temporary write protection.\n \"pwron\" - Set write protection until the next poweron.\n<start block> specifies the first block of the protected area.\n<blocks> specifies the size of the protected area in blocks.\nNOTE! The area must start and end on Write Protect Group\nboundries, Use the \"writeprotect user get\" command to get the\nWrite Protect Group size.",
+#endif /* DANGEROUS_COMMANDS_ENABLED */
+ NULL
+ },
+ { do_writeprotect_user_get, -1,
+ "writeprotect user get", "<device>\n"
+ "Print the user areas write protect configuration for <device>.",
NULL
},
{ do_disable_512B_emulation, -1,
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/mmc-utils-0.1+git.20160511/mmc.h new/mmc-utils-0.1+git.20160623/mmc.h
--- old/mmc-utils-0.1+git.20160511/mmc.h 2016-05-12 22:45:28.000000000 +0200
+++ new/mmc-utils-0.1+git.20160623/mmc.h 2016-06-29 17:19:02.000000000 +0200
@@ -39,6 +39,9 @@
#define MMC_READ_MULTIPLE_BLOCK 18 /* adtc [31:0] data addr R1 */
#define MMC_WRITE_BLOCK 24 /* adtc [31:0] data addr R1 */
#define MMC_WRITE_MULTIPLE_BLOCK 25 /* adtc R1 */
+#define MMC_SET_WRITE_PROT 28 /* ac [31:0] data addr R1b */
+#define MMC_CLEAR_WRITE_PROT 29 /* ac [31:0] data addr R1b */
+#define MMC_SEND_WRITE_PROT_TYPE 31 /* ac [31:0] data addr R1 */
/*
* EXT_CSD fields
@@ -52,6 +55,8 @@
#define EXT_CSD_FFU_ARG_2 489 /* RO */
#define EXT_CSD_FFU_ARG_1 488 /* RO */
#define EXT_CSD_FFU_ARG_0 487 /* RO */
+#define EXT_CSD_CMDQ_DEPTH 307 /* RO */
+#define EXT_CSD_CMDQ_SUPPORT 308 /* RO */
#define EXT_CSD_NUM_OF_FW_SEC_PROG_3 305 /* RO */
#define EXT_CSD_NUM_OF_FW_SEC_PROG_2 304 /* RO */
#define EXT_CSD_NUM_OF_FW_SEC_PROG_1 303 /* RO */
@@ -62,6 +67,8 @@
#define EXT_CSD_CACHE_SIZE_1 250
#define EXT_CSD_CACHE_SIZE_0 249
#define EXT_CSD_BOOT_INFO 228 /* R/W */
+#define EXT_CSD_HC_ERASE_GRP_SIZE 224
+#define EXT_CSD_HC_WP_GRP_SIZE 221
#define EXT_CSD_SEC_COUNT_3 215
#define EXT_CSD_SEC_COUNT_2 214
#define EXT_CSD_SEC_COUNT_1 213
@@ -73,6 +80,7 @@
#define EXT_CSD_BOOT_BUS_CONDITIONS 177
#define EXT_CSD_ERASE_GROUP_DEF 175
#define EXT_CSD_BOOT_WP 173
+#define EXT_CSD_USER_WP 171
#define EXT_CSD_FW_CONFIG 169 /* R/W */
#define EXT_CSD_WR_REL_SET 167
#define EXT_CSD_WR_REL_PARAM 166
@@ -113,6 +121,7 @@
#define EXT_CSD_MODE_CONFIG 30
#define EXT_CSD_MODE_OPERATION_CODES 29 /* W */
#define EXT_CSD_FFU_STATUS 26 /* R */
+#define EXT_CSD_CMDQ_MODE_EN 15 /* R/W */
/*
* WR_REL_PARAM field definitions
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/mmc-utils-0.1+git.20160511/mmc_cmds.c new/mmc-utils-0.1+git.20160623/mmc_cmds.c
--- old/mmc-utils-0.1+git.20160511/mmc_cmds.c 2016-05-12 22:45:28.000000000 +0200
+++ new/mmc-utils-0.1+git.20160623/mmc_cmds.c 2016-06-29 17:19:02.000000000 +0200
@@ -32,11 +32,29 @@
#include
#include
#include
+#include
#include "mmc.h"
#include "mmc_cmds.h"
#include "3rdparty/hmac_sha/hmac_sha2.h"
+#define WP_BLKS_PER_QUERY 32
+
+#define USER_WP_PERM_PSWD_DIS 0x80
+#define USER_WP_CD_PERM_WP_DIS 0x40
+#define USER_WP_US_PERM_WP_DIS 0x10
+#define USER_WP_US_PWR_WP_DIS 0x08
+#define USER_WP_US_PERM_WP_EN 0x04
+#define USER_WP_US_PWR_WP_EN 0x01
+#define USER_WP_CLEAR (USER_WP_US_PERM_WP_DIS | USER_WP_US_PWR_WP_DIS \
+ | USER_WP_US_PERM_WP_EN | USER_WP_US_PWR_WP_EN)
+
+#define WPTYPE_NONE 0
+#define WPTYPE_TEMP 1
+#define WPTYPE_PWRON 2
+#define WPTYPE_PERM 3
+
+
int read_extcsd(int fd, __u8 *ext_csd)
{
int ret = 0;
@@ -98,7 +116,69 @@
return ret;
}
-void print_writeprotect_status(__u8 *ext_csd)
+static __u32 get_size_in_blks(int fd)
+{
+ int res;
+ int size;
+
+ res = ioctl(fd, BLKGETSIZE, &size);
+ if (res) {
+ fprintf(stderr, "Error getting device size, errno: %d\n",
+ errno);
+ perror("");
+ return -1;
+ }
+ return size;
+}
+
+static int set_write_protect(int fd, __u32 blk_addr, int on_off)
+{
+ int ret = 0;
+ struct mmc_ioc_cmd idata;
+
+ memset(&idata, 0, sizeof(idata));
+ idata.write_flag = 1;
+ if (on_off)
+ idata.opcode = MMC_SET_WRITE_PROT;
+ else
+ idata.opcode = MMC_CLEAR_WRITE_PROT;
+ idata.arg = blk_addr;
+ idata.flags = MMC_RSP_SPI_R1B | MMC_RSP_R1B | MMC_CMD_AC;
+
+ ret = ioctl(fd, MMC_IOC_CMD, &idata);
+ if (ret)
+ perror("ioctl");
+
+ return ret;
+}
+
+static int send_write_protect_type(int fd, __u32 blk_addr, __u64 *group_bits)
+{
+ int ret = 0;
+ struct mmc_ioc_cmd idata;
+ __u8 buf[8];
+ __u64 bits = 0;
+ int x;
+
+ memset(&idata, 0, sizeof(idata));
+ idata.write_flag = 0;
+ idata.opcode = MMC_SEND_WRITE_PROT_TYPE;
+ idata.blksz = 8,
+ idata.blocks = 1,
+ idata.arg = blk_addr;
+ idata.flags = MMC_RSP_SPI_R1 | MMC_RSP_R1 | MMC_CMD_ADTC;
+ mmc_ioc_cmd_set_data(idata, buf);
+
+ ret = ioctl(fd, MMC_IOC_CMD, &idata);
+ if (ret)
+ perror("ioctl");
+ for (x = 0; x < sizeof(buf); x++)
+ bits |= (__u64)(buf[7 - x]) << (x * 8);
+ *group_bits = bits;
+ return ret;
+}
+
+static void print_writeprotect_boot_status(__u8 *ext_csd)
{
__u8 reg;
__u8 ext_csd_rev = ext_csd[EXT_CSD_REV];
@@ -132,14 +212,28 @@
}
}
-int do_writeprotect_get(int nargs, char **argv)
+static int get_wp_group_size_in_blks(__u8 *ext_csd, __u32 *size)
+{
+ __u8 ext_csd_rev = ext_csd[EXT_CSD_REV];
+
+ if ((ext_csd_rev < 5) || (ext_csd[EXT_CSD_ERASE_GROUP_DEF] == 0))
+ return 1;
+
+ *size = ext_csd[EXT_CSD_HC_ERASE_GRP_SIZE] *
+ ext_csd[EXT_CSD_HC_WP_GRP_SIZE] * 1024;
+ return 0;
+}
+
+
+int do_writeprotect_boot_get(int nargs, char **argv)
{
__u8 ext_csd[512];
int fd, ret;
char *device;
- CHECK(nargs != 2, "Usage: mmc writeprotect get \n",
- exit(1));
+ CHECK(nargs != 2,
+ "Usage: mmc writeprotect boot get \n",
+ exit(1));
device = argv[1];
@@ -155,19 +249,20 @@
exit(1);
}
- print_writeprotect_status(ext_csd);
+ print_writeprotect_boot_status(ext_csd);
return ret;
}
-int do_writeprotect_set(int nargs, char **argv)
+int do_writeprotect_boot_set(int nargs, char **argv)
{
__u8 ext_csd[512], value;
int fd, ret;
char *device;
- CHECK(nargs != 2, "Usage: mmc writeprotect set \n",
- exit(1));
+ CHECK(nargs != 2,
+ "Usage: mmc writeprotect boot set \n",
+ exit(1));
device = argv[1];
@@ -196,6 +291,191 @@
return ret;
}
+static char *prot_desc[] = {
+ "No",
+ "Temporary",
+ "Power-on",
+ "Permanent"
+};
+
+static void print_wp_status(__u32 wp_sizeblks, __u32 start_group,
+ __u32 end_group, int rptype)
+{
+ printf("Write Protect Groups %d-%d (Blocks %d-%d), ",
+ start_group, end_group,
+ start_group * wp_sizeblks, ((end_group + 1) * wp_sizeblks) - 1);
+ printf("%s Write Protection\n", prot_desc[rptype]);
+}
+
+
+int do_writeprotect_user_get(int nargs, char **argv)
+{
+ __u8 ext_csd[512];
+ int fd, ret;
+ char *device;
+ int x;
+ int y = 0;
+ __u32 wp_sizeblks;
+ __u32 dev_sizeblks;
+ __u32 cnt;
+ __u64 bits;
+ __u32 wpblk;
+ __u32 last_wpblk = 0;
+ __u32 prot;
+ __u32 last_prot = -1;
+ int remain;
+
+ CHECK(nargs != 2,
+ "Usage: mmc writeprotect user get \n",
+ exit(1));
+
+ device = argv[1];
+
+ fd = open(device, O_RDWR);
+ if (fd < 0) {
+ perror("open");
+ exit(1);
+ }
+ ret = read_extcsd(fd, ext_csd);
+ if (ret) {
+ fprintf(stderr, "Could not read EXT_CSD from %s\n", device);
+ exit(1);
+ }
+
+ ret = get_wp_group_size_in_blks(ext_csd, &wp_sizeblks);
+ if (ret)
+ exit(1);
+ printf("Write Protect Group size in blocks/bytes: %d/%d\n",
+ wp_sizeblks, wp_sizeblks * 512);
+ dev_sizeblks = get_size_in_blks(fd);
+ cnt = dev_sizeblks / wp_sizeblks;
+ for (x = 0; x < cnt; x += WP_BLKS_PER_QUERY) {
+ ret = send_write_protect_type(fd, x * wp_sizeblks, &bits);
+ if (ret)
+ break;
+ remain = cnt - x;
+ if (remain > WP_BLKS_PER_QUERY)
+ remain = WP_BLKS_PER_QUERY;
+ for (y = 0; y < remain; y++) {
+ prot = (bits >> (y * 2)) & 0x3;
+ if (prot != last_prot) {
+ /* not first time */
+ if (last_prot != -1) {
+ wpblk = x + y;
+ print_wp_status(wp_sizeblks,
+ last_wpblk,
+ wpblk - 1,
+ last_prot);
+ last_wpblk = wpblk;
+ }
+ last_prot = prot;
+ }
+ }
+ }
+ if (last_wpblk != (x + y - 1))
+ print_wp_status(wp_sizeblks, last_wpblk, cnt - 1, last_prot);
+
+ return ret;
+}
+
+int do_writeprotect_user_set(int nargs, char **argv)
+{
+ __u8 ext_csd[512];
+ int fd, ret;
+ char *device;
+ int blk_start;
+ int blk_cnt;
+ __u32 wp_blks;
+ __u8 user_wp;
+ int x;
+ int wptype;
+
+ if (nargs != 5)
+ goto usage;
+ device = argv[4];
+ fd = open(device, O_RDWR);
+ if (fd < 0) {
+ perror("open");
+ exit(1);
+ }
+ if (!strcmp(argv[1], "none")) {
+ wptype = WPTYPE_NONE;
+ } else if (!strcmp(argv[1], "temp")) {
+ wptype = WPTYPE_TEMP;
+ } else if (!strcmp(argv[1], "pwron")) {
+ wptype = WPTYPE_PWRON;
+#ifdef DANGEROUS_COMMANDS_ENABLED
+ } else if (!strcmp(argv[1], "perm")) {
+ wptype = WPTYPE_PERM;
+#endif /* DANGEROUS_COMMANDS_ENABLED */
+ } else {
+ fprintf(stderr, "Error, invalid \"type\"\n");
+ goto usage;
+ }
+ ret = read_extcsd(fd, ext_csd);
+ if (ret) {
+ fprintf(stderr, "Could not read EXT_CSD from %s\n", device);
+ exit(1);
+ }
+ ret = get_wp_group_size_in_blks(ext_csd, &wp_blks);
+ if (ret) {
+ fprintf(stderr, "Operation not supported for this device\n");
+ exit(1);
+ }
+ blk_start = strtol(argv[2], NULL, 0);
+ blk_cnt = strtol(argv[3], NULL, 0);
+ if ((blk_start % wp_blks) || (blk_cnt % wp_blks)) {
+ fprintf(stderr, "<start block> and <blocks> must be a ");
+ fprintf(stderr, "multiple of the Write Protect Group (%d)\n",
+ wp_blks);
+ exit(1);
+ }
+ if (wptype != WPTYPE_NONE) {
+ user_wp = ext_csd[EXT_CSD_USER_WP];
+ user_wp &= ~USER_WP_CLEAR;
+ switch (wptype) {
+ case WPTYPE_TEMP:
+ break;
+ case WPTYPE_PWRON:
+ user_wp |= USER_WP_US_PWR_WP_EN;
+ break;
+ case WPTYPE_PERM:
+ user_wp |= USER_WP_US_PERM_WP_EN;
+ break;
+ }
+ if (user_wp != ext_csd[EXT_CSD_USER_WP]) {
+ ret = write_extcsd_value(fd, EXT_CSD_USER_WP, user_wp);
+ if (ret) {
+ fprintf(stderr, "Error setting EXT_CSD\n");
+ exit(1);
+ }
+ }
+ }
+ for (x = 0; x < blk_cnt; x += wp_blks) {
+ ret = set_write_protect(fd, blk_start + x,
+ wptype != WPTYPE_NONE);
+ if (ret) {
+ fprintf(stderr,
+ "Could not set write protect for %s\n", device);
+ exit(1);
+ }
+ }
+ if (wptype != WPTYPE_NONE) {
+ ret = write_extcsd_value(fd, EXT_CSD_USER_WP,
+ ext_csd[EXT_CSD_USER_WP]);
+ if (ret) {
+ fprintf(stderr, "Error restoring EXT_CSD\n");
+ exit(1);
+ }
+ }
+ return ret;
+
+usage:
+ fprintf(stderr,
+ "Usage: mmc writeprotect user set <type><start block><blocks><device>\n");
+ exit(1);
+}
+
int do_disable_512B_emulation(int nargs, char **argv)
{
__u8 ext_csd[512], native_sector_size, data_sector_size, wr_rel_param;
@@ -1278,7 +1558,7 @@
printf("High-density erase group definition"
" [ERASE_GROUP_DEF: 0x%02x]\n", ext_csd[EXT_CSD_ERASE_GROUP_DEF]);
- print_writeprotect_status(ext_csd);
+ print_writeprotect_boot_status(ext_csd);
if (ext_csd_rev >= 5) {
/* A441]: reserved [172] */
@@ -1443,6 +1723,15 @@
printf("eMMC Firmware Version: %s\n",
(char*)&ext_csd[EXT_CSD_FIRMWARE_VERSION]);
}
+
+ if (ext_csd_rev >= 8) {
+ printf("Command Queue Support [CMDQ_SUPPORT]: 0x%02x\n",
+ ext_csd[EXT_CSD_CMDQ_SUPPORT]);
+ printf("Command Queue Depth [CMDQ_DEPTH]: %u\n",
+ (ext_csd[EXT_CSD_CMDQ_DEPTH] & 0x1f) + 1);
+ printf("Command Enabled [CMDQ_MODE_EN]: 0x%02x\n",
+ ext_csd[EXT_CSD_CMDQ_MODE_EN]);
+ }
out_free:
return ret;
}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/mmc-utils-0.1+git.20160511/mmc_cmds.h new/mmc-utils-0.1+git.20160623/mmc_cmds.h
--- old/mmc-utils-0.1+git.20160511/mmc_cmds.h 2016-05-12 22:45:28.000000000 +0200
+++ new/mmc-utils-0.1+git.20160623/mmc_cmds.h 2016-06-29 17:19:02.000000000 +0200
@@ -20,8 +20,10 @@
/* mmc_cmds.c */
int do_read_extcsd(int nargs, char **argv);
int do_write_extcsd(int nargs, char **argv);
-int do_writeprotect_get(int nargs, char **argv);
-int do_writeprotect_set(int nargs, char **argv);
+int do_writeprotect_boot_get(int nargs, char **argv);
+int do_writeprotect_boot_set(int nargs, char **argv);
+int do_writeprotect_user_get(int nargs, char **argv);
+int do_writeprotect_user_set(int nargs, char **argv);
int do_disable_512B_emulation(int nargs, char **argv);
int do_write_boot_en(int nargs, char **argv);
int do_boot_bus_conditions_set(int nargs, char **argv);