aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorIdan Kahlon <idanx.kahlon@intel.com>2014-11-13 15:47:20 +0200
committerEmmanuel Grumbach <emmanuel.grumbach@intel.com>2014-12-01 12:04:43 +0200
commita4e5df283c9a84b29100a046e64f35bfb1660a9c (patch)
tree416f101c74ae1c2331b25ea4aa2d92483beca537 /drivers
parentiwlwifi: mvm: add channel information to the netdetect notifications (diff)
downloadlinux-dev-a4e5df283c9a84b29100a046e64f35bfb1660a9c.tar.xz
linux-dev-a4e5df283c9a84b29100a046e64f35bfb1660a9c.zip
iwlwifi: mvm: support NVM file with header
Handle NVM file header. When NVM header detected, skip the header and reading only the sections data. Signed-off-by: Idan Kahlon <idanx.kahlon@intel.com> Reviewed-by: Johannes Berg <johannes.berg@intel.com> Signed-off-by: Emmanuel Grumbach <emmanuel.grumbach@intel.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/net/wireless/iwlwifi/mvm/nvm.c31
1 files changed, 23 insertions, 8 deletions
diff --git a/drivers/net/wireless/iwlwifi/mvm/nvm.c b/drivers/net/wireless/iwlwifi/mvm/nvm.c
index af074563e770..d55fd8e3654c 100644
--- a/drivers/net/wireless/iwlwifi/mvm/nvm.c
+++ b/drivers/net/wireless/iwlwifi/mvm/nvm.c
@@ -339,11 +339,15 @@ static int iwl_mvm_read_external_nvm(struct iwl_mvm *mvm)
} *file_sec;
const u8 *eof, *temp;
int max_section_size;
+ const __le32 *dword_buff;
#define NVM_WORD1_LEN(x) (8 * (x & 0x03FF))
#define NVM_WORD2_ID(x) (x >> 12)
#define NVM_WORD2_LEN_FAMILY_8000(x) (2 * ((x & 0xFF) << 8 | x >> 8))
#define NVM_WORD1_ID_FAMILY_8000(x) (x >> 4)
+#define NVM_HEADER_0 (0x2A504C54)
+#define NVM_HEADER_1 (0x4E564D2A)
+#define NVM_HEADER_SIZE (4 * sizeof(u32))
IWL_DEBUG_EEPROM(mvm->trans->dev, "Read from external NVM\n");
@@ -372,12 +376,6 @@ static int iwl_mvm_read_external_nvm(struct iwl_mvm *mvm)
IWL_INFO(mvm, "Loaded NVM file %s (%zu bytes)\n",
mvm->nvm_file_name, fw_entry->size);
- if (fw_entry->size < sizeof(*file_sec)) {
- IWL_ERR(mvm, "NVM file too small\n");
- ret = -EINVAL;
- goto out;
- }
-
if (fw_entry->size > MAX_NVM_FILE_LEN) {
IWL_ERR(mvm, "NVM file too large\n");
ret = -EINVAL;
@@ -385,8 +383,25 @@ static int iwl_mvm_read_external_nvm(struct iwl_mvm *mvm)
}
eof = fw_entry->data + fw_entry->size;
-
- file_sec = (void *)fw_entry->data;
+ dword_buff = (__le32 *)fw_entry->data;
+
+ /* some NVM file will contain a header.
+ * The header is identified by 2 dwords header as follow:
+ * dword[0] = 0x2A504C54
+ * dword[1] = 0x4E564D2A
+ *
+ * This header must be skipped when providing the NVM data to the FW.
+ */
+ if (fw_entry->size > NVM_HEADER_SIZE &&
+ dword_buff[0] == cpu_to_le32(NVM_HEADER_0) &&
+ dword_buff[1] == cpu_to_le32(NVM_HEADER_1)) {
+ file_sec = (void *)(fw_entry->data + NVM_HEADER_SIZE);
+ IWL_INFO(mvm, "NVM Version %08X\n", le32_to_cpu(dword_buff[2]));
+ IWL_INFO(mvm, "NVM Manufacturing date %08X\n",
+ le32_to_cpu(dword_buff[3]));
+ } else {
+ file_sec = (void *)fw_entry->data;
+ }
while (true) {
if (file_sec->data > eof) {