/* Init-CSR owner IDs for firmware map to firmware IDs which start at 4. * Lower IDs are reserved for target and loader IDs.
*/ #define NFFW_FWID_EXT 3 /* For active MEs that we didn't load. */ #define NFFW_FWID_BASE 4
#define NFFW_FWID_ALL 255
/* * NFFW_INFO_VERSION history: * 0: This was never actually used (before versioning), but it refers to * the previous struct which had FWINFO_CNT = MEINFO_CNT = 120 that later * changed to 200. * 1: First versioned struct, with * FWINFO_CNT = 120 * MEINFO_CNT = 120 * 2: FWINFO_CNT = 200 * MEINFO_CNT = 200
*/ #define NFFW_INFO_VERSION_CURRENT 2
/* Enough for all current chip families */ #define NFFW_MEINFO_CNT_V1 120 #define NFFW_FWINFO_CNT_V1 120 #define NFFW_MEINFO_CNT_V2 200 #define NFFW_FWINFO_CNT_V2 200
/* Work in 32-bit words to make cross-platform endianness easier to handle */
/* flg_info_version = flags[0]<27:16> * This is a small version counter intended only to detect if the current * implementation can read the current struct. Struct changes should be very * rare and as such a 12-bit counter should cover large spans of time. By the * time it wraps around, we don't expect to have 4096 versions of this struct * to be in use at the same time.
*/ static u32 nffw_res_info_version_get(conststruct nfp_nffw_info_data *res)
{ return (le32_to_cpu(res->flags[0]) >> 16) & 0xfff;
}
staticunsignedint
nffw_res_fwinfos(struct nfp_nffw_info_data *fwinf, struct nffw_fwinfo **arr)
{ /* For the this code, version 0 is most likely to be * version 1 in this case. Since the kernel driver * does not take responsibility for initialising the * nfp.nffw resource, any previous code (CA firmware or * userspace) that left the version 0 and did set * the init flag is going to be version 1.
*/ switch (nffw_res_info_version_get(fwinf)) { case 0: case 1:
*arr = &fwinf->info.v1.fwinfo[0]; return NFFW_FWINFO_CNT_V1; case 2:
*arr = &fwinf->info.v2.fwinfo[0]; return NFFW_FWINFO_CNT_V2; default:
*arr = NULL; return 0;
}
}
/** * nfp_nffw_info_open() - Acquire the lock on the NFFW table * @cpp: NFP CPP handle * * Return: pointer to nfp_nffw_info object or ERR_PTR()
*/ struct nfp_nffw_info *nfp_nffw_info_open(struct nfp_cpp *cpp)
{ struct nfp_nffw_info_data *fwinf; struct nfp_nffw_info *state;
u32 info_ver; int err;
state = kzalloc(sizeof(*state), GFP_KERNEL); if (!state) return ERR_PTR(-ENOMEM);
state->res = nfp_resource_acquire(cpp, NFP_RESOURCE_NFP_NFFW); if (IS_ERR(state->res)) goto err_free;
fwinf = &state->fwinf;
if (sizeof(*fwinf) > nfp_resource_size(state->res)) goto err_release;
/** * nfp_nffw_info_close() - Release the lock on the NFFW table and free state * @state: NFP FW info state
*/ void nfp_nffw_info_close(struct nfp_nffw_info *state)
{
nfp_resource_release(state->res);
kfree(state);
}
/** * nfp_nffw_info_fwid_first() - Return the first firmware ID in the NFFW * @state: NFP FW info state * * Return: First NFFW firmware info, NULL on failure
*/ staticstruct nffw_fwinfo *nfp_nffw_info_fwid_first(struct nfp_nffw_info *state)
{ struct nffw_fwinfo *fwinfo; unsignedint cnt, i;
cnt = nffw_res_fwinfos(&state->fwinf, &fwinfo); if (!cnt) return NULL;
for (i = 0; i < cnt; i++) if (nffw_fwinfo_loaded_get(&fwinfo[i])) return &fwinfo[i];
return NULL;
}
/** * nfp_nffw_info_mip_first() - Retrieve the location of the first FW's MIP * @state: NFP FW info state * @cpp_id: Pointer to the CPP ID of the MIP * @off: Pointer to the CPP Address of the MIP * * Return: 0, or -ERRNO
*/ int nfp_nffw_info_mip_first(struct nfp_nffw_info *state, u32 *cpp_id, u64 *off)
{ struct nffw_fwinfo *fwinfo;
fwinfo = nfp_nffw_info_fwid_first(state); if (!fwinfo) return -EINVAL;
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.