예제 #1
0
파일: sdma_v4_0.c 프로젝트: asmalldev/linux
// emulation only, won't work on real chip
// vega10 real chip need to use PSP to load firmware
static int sdma_v4_0_init_microcode(struct amdgpu_device *adev)
{
	const char *chip_name;
	char fw_name[30];
	int err = 0, i;
	struct amdgpu_firmware_info *info = NULL;
	const struct common_firmware_header *header = NULL;
	const struct sdma_firmware_header_v1_0 *hdr;

	DRM_DEBUG("\n");

	switch (adev->asic_type) {
	case CHIP_VEGA10:
		chip_name = "vega10";
		break;
	default:
		BUG();
	}

	for (i = 0; i < adev->sdma.num_instances; i++) {
		if (i == 0)
			snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_sdma.bin", chip_name);
		else
			snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_sdma1.bin", chip_name);
		err = request_firmware(&adev->sdma.instance[i].fw, fw_name, adev->dev);
		if (err)
			goto out;
		err = amdgpu_ucode_validate(adev->sdma.instance[i].fw);
		if (err)
			goto out;
		hdr = (const struct sdma_firmware_header_v1_0 *)adev->sdma.instance[i].fw->data;
		adev->sdma.instance[i].fw_version = le32_to_cpu(hdr->header.ucode_version);
		adev->sdma.instance[i].feature_version = le32_to_cpu(hdr->ucode_feature_version);
		if (adev->sdma.instance[i].feature_version >= 20)
			adev->sdma.instance[i].burst_nop = true;
		DRM_DEBUG("psp_load == '%s'\n",
				adev->firmware.load_type == AMDGPU_FW_LOAD_PSP ? "true" : "false");

		if (adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) {
			info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SDMA0 + i];
			info->ucode_id = AMDGPU_UCODE_ID_SDMA0 + i;
			info->fw = adev->sdma.instance[i].fw;
			header = (const struct common_firmware_header *)info->fw->data;
			adev->firmware.fw_size +=
				ALIGN(le32_to_cpu(header->ucode_size_bytes), PAGE_SIZE);
		}
	}
out:
	if (err) {
		DRM_ERROR("sdma_v4_0: Failed to load firmware \"%s\"\n", fw_name);
		for (i = 0; i < adev->sdma.num_instances; i++) {
			release_firmware(adev->sdma.instance[i].fw);
			adev->sdma.instance[i].fw = NULL;
		}
	}
	return err;
}
예제 #2
0
/**
 * sdma_v3_0_init_microcode - load ucode images from disk
 *
 * @adev: amdgpu_device pointer
 *
 * Use the firmware interface to load the ucode images into
 * the driver (not loaded into hw).
 * Returns 0 on success, error on failure.
 */
static int sdma_v3_0_init_microcode(struct amdgpu_device *adev)
{
	const char *chip_name;
	char fw_name[30];
	int err, i;
	struct amdgpu_firmware_info *info = NULL;
	const struct common_firmware_header *header = NULL;
	const struct sdma_firmware_header_v1_0 *hdr;

	DRM_DEBUG("\n");

	switch (adev->asic_type) {
	case CHIP_TONGA:
		chip_name = "tonga";
		break;
	case CHIP_CARRIZO:
		chip_name = "carrizo";
		break;
	default: BUG();
	}

	for (i = 0; i < SDMA_MAX_INSTANCE; i++) {
		if (i == 0)
			snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_sdma.bin", chip_name);
		else
			snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_sdma1.bin", chip_name);
		err = request_firmware(&adev->sdma[i].fw, fw_name, adev->dev);
		if (err)
			goto out;
		err = amdgpu_ucode_validate(adev->sdma[i].fw);
		if (err)
			goto out;
		hdr = (const struct sdma_firmware_header_v1_0 *)adev->sdma[i].fw->data;
		adev->sdma[i].fw_version = le32_to_cpu(hdr->header.ucode_version);
		adev->sdma[i].feature_version = le32_to_cpu(hdr->ucode_feature_version);

		if (adev->firmware.smu_load) {
			info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SDMA0 + i];
			info->ucode_id = AMDGPU_UCODE_ID_SDMA0 + i;
			info->fw = adev->sdma[i].fw;
			header = (const struct common_firmware_header *)info->fw->data;
			adev->firmware.fw_size +=
				ALIGN(le32_to_cpu(header->ucode_size_bytes), PAGE_SIZE);
		}
	}
out:
	if (err) {
		printk(KERN_ERR
		       "sdma_v3_0: Failed to load firmware \"%s\"\n",
		       fw_name);
		for (i = 0; i < SDMA_MAX_INSTANCE; i++) {
			release_firmware(adev->sdma[i].fw);
			adev->sdma[i].fw = NULL;
		}
	}
	return err;
}
예제 #3
0
파일: cik_sdma.c 프로젝트: rushgun/linux-1
/**
 * cik_sdma_init_microcode - load ucode images from disk
 *
 * @adev: amdgpu_device pointer
 *
 * Use the firmware interface to load the ucode images into
 * the driver (not loaded into hw).
 * Returns 0 on success, error on failure.
 */
static int cik_sdma_init_microcode(struct amdgpu_device *adev)
{
    const char *chip_name;
    char fw_name[30];
    int err, i;

    DRM_DEBUG("\n");

    switch (adev->asic_type) {
    case CHIP_BONAIRE:
        chip_name = "bonaire";
        break;
    case CHIP_HAWAII:
        chip_name = "hawaii";
        break;
    case CHIP_KAVERI:
        chip_name = "kaveri";
        break;
    case CHIP_KABINI:
        chip_name = "kabini";
        break;
    case CHIP_MULLINS:
        chip_name = "mullins";
        break;
    default:
        BUG();
    }

    for (i = 0; i < SDMA_MAX_INSTANCE; i++) {
        if (i == 0)
            snprintf(fw_name, sizeof(fw_name), "radeon/%s_sdma.bin", chip_name);
        else
            snprintf(fw_name, sizeof(fw_name), "radeon/%s_sdma1.bin", chip_name);
        err = request_firmware(&adev->sdma[i].fw, fw_name, adev->dev);
        if (err)
            goto out;
        err = amdgpu_ucode_validate(adev->sdma[i].fw);
    }
out:
    if (err) {
        printk(KERN_ERR
               "cik_sdma: Failed to load firmware \"%s\"\n",
               fw_name);
        for (i = 0; i < SDMA_MAX_INSTANCE; i++) {
            release_firmware(adev->sdma[i].fw);
            adev->sdma[i].fw = NULL;
        }
    }
    return err;
}
예제 #4
0
파일: tonga_dpm.c 프로젝트: Chong-Li/cse522
static int tonga_dpm_init_microcode(struct amdgpu_device *adev)
{
	char fw_name[30] = "amdgpu/tonga_smc.bin";
	int err;
	err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
	if (err)
		goto out;
	err = amdgpu_ucode_validate(adev->pm.fw);

out:
	if (err) {
		DRM_ERROR("Failed to load firmware \"%s\"", fw_name);
		release_firmware(adev->pm.fw);
		adev->pm.fw = NULL;
	}
	return err;
}
예제 #5
0
int psp_v10_0_init_microcode(struct psp_context *psp)
{
	struct amdgpu_device *adev = psp->adev;
	const char *chip_name;
	char fw_name[30];
	int err = 0;
	const struct psp_firmware_header_v1_0 *hdr;

	DRM_DEBUG("\n");

	switch (adev->asic_type) {
	case CHIP_RAVEN:
		chip_name = "raven";
		break;
	default: BUG();
	}

	snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_asd.bin", chip_name);
	err = request_firmware(&adev->psp.asd_fw, fw_name, adev->dev);
	if (err)
		goto out;

	err = amdgpu_ucode_validate(adev->psp.asd_fw);
	if (err)
		goto out;

	hdr = (const struct psp_firmware_header_v1_0 *)adev->psp.asd_fw->data;
	adev->psp.asd_fw_version = le32_to_cpu(hdr->header.ucode_version);
	adev->psp.asd_feature_version = le32_to_cpu(hdr->ucode_feature_version);
	adev->psp.asd_ucode_size = le32_to_cpu(hdr->header.ucode_size_bytes);
	adev->psp.asd_start_addr = (uint8_t *)hdr +
				le32_to_cpu(hdr->header.ucode_array_offset_bytes);

	return 0;
out:
	if (err) {
		dev_err(adev->dev,
			"psp v10.0: Failed to load firmware \"%s\"\n",
			fw_name);
		release_firmware(adev->psp.asd_fw);
		adev->psp.asd_fw = NULL;
	}

	return err;
}
예제 #6
0
static int iceland_dpm_init_microcode(struct amdgpu_device *adev)
{
	char fw_name[30] = "/*(DEBLOBBED)*/";
	int err;

	err = reject_firmware(&adev->pm.fw, fw_name, adev->dev);
	if (err)
		goto out;
	err = amdgpu_ucode_validate(adev->pm.fw);

out:
	if (err) {
		DRM_ERROR("Failed to load firmware \"%s\"", fw_name);
		release_firmware(adev->pm.fw);
		adev->pm.fw = NULL;
	}
	return err;
}
예제 #7
0
파일: gmc_v7_0.c 프로젝트: ssdxiao/linux
/**
 * gmc_v7_0_init_microcode - load ucode images from disk
 *
 * @adev: amdgpu_device pointer
 *
 * Use the firmware interface to load the ucode images into
 * the driver (not loaded into hw).
 * Returns 0 on success, error on failure.
 */
static int gmc_v7_0_init_microcode(struct amdgpu_device *adev)
{
	const char *chip_name;
	char fw_name[30];
	int err;

	DRM_DEBUG("\n");

	switch (adev->asic_type) {
	case CHIP_BONAIRE:
		chip_name = "bonaire";
		break;
	case CHIP_HAWAII:
		chip_name = "hawaii";
		break;
	case CHIP_TOPAZ:
		chip_name = "topaz";
		break;
	case CHIP_KAVERI:
	case CHIP_KABINI:
	case CHIP_MULLINS:
		return 0;
	default: BUG();
	}

	if (adev->asic_type == CHIP_TOPAZ)
		snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mc.bin", chip_name);
	else
		snprintf(fw_name, sizeof(fw_name), "radeon/%s_mc.bin", chip_name);

	err = request_firmware(&adev->mc.fw, fw_name, adev->dev);
	if (err)
		goto out;
	err = amdgpu_ucode_validate(adev->mc.fw);

out:
	if (err) {
		pr_err("cik_mc: Failed to load firmware \"%s\"\n", fw_name);
		release_firmware(adev->mc.fw);
		adev->mc.fw = NULL;
	}
	return err;
}
예제 #8
0
static int psp_v11_0_init_microcode(struct psp_context *psp)
{
	struct amdgpu_device *adev = psp->adev;
	const char *chip_name;
	char fw_name[30];
	int err = 0;
	const struct psp_firmware_header_v1_0 *sos_hdr;
	const struct psp_firmware_header_v1_0 *asd_hdr;
	const struct ta_firmware_header_v1_0 *ta_hdr;

	DRM_DEBUG("\n");

	switch (adev->asic_type) {
	case CHIP_VEGA20:
		chip_name = "vega20";
		break;
	default:
		BUG();
	}

	snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_sos.bin", chip_name);
	err = request_firmware(&adev->psp.sos_fw, fw_name, adev->dev);
	if (err)
		goto out;

	err = amdgpu_ucode_validate(adev->psp.sos_fw);
	if (err)
		goto out;

	sos_hdr = (const struct psp_firmware_header_v1_0 *)adev->psp.sos_fw->data;
	adev->psp.sos_fw_version = le32_to_cpu(sos_hdr->header.ucode_version);
	adev->psp.sos_feature_version = le32_to_cpu(sos_hdr->ucode_feature_version);
	adev->psp.sos_bin_size = le32_to_cpu(sos_hdr->sos_size_bytes);
	adev->psp.sys_bin_size = le32_to_cpu(sos_hdr->header.ucode_size_bytes) -
					le32_to_cpu(sos_hdr->sos_size_bytes);
	adev->psp.sys_start_addr = (uint8_t *)sos_hdr +
				le32_to_cpu(sos_hdr->header.ucode_array_offset_bytes);
	adev->psp.sos_start_addr = (uint8_t *)adev->psp.sys_start_addr +
				le32_to_cpu(sos_hdr->sos_offset_bytes);

	snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_asd.bin", chip_name);
	err = request_firmware(&adev->psp.asd_fw, fw_name, adev->dev);
	if (err)
		goto out1;

	err = amdgpu_ucode_validate(adev->psp.asd_fw);
	if (err)
		goto out1;

	asd_hdr = (const struct psp_firmware_header_v1_0 *)adev->psp.asd_fw->data;
	adev->psp.asd_fw_version = le32_to_cpu(asd_hdr->header.ucode_version);
	adev->psp.asd_feature_version = le32_to_cpu(asd_hdr->ucode_feature_version);
	adev->psp.asd_ucode_size = le32_to_cpu(asd_hdr->header.ucode_size_bytes);
	adev->psp.asd_start_addr = (uint8_t *)asd_hdr +
				le32_to_cpu(asd_hdr->header.ucode_array_offset_bytes);

	snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ta.bin", chip_name);
	err = request_firmware(&adev->psp.ta_fw, fw_name, adev->dev);
	if (err) {
		release_firmware(adev->psp.ta_fw);
		adev->psp.ta_fw = NULL;
		dev_info(adev->dev,
			 "psp v11.0: Failed to load firmware \"%s\"\n", fw_name);
	} else {
		err = amdgpu_ucode_validate(adev->psp.ta_fw);
		if (err)
			goto out2;

		ta_hdr = (const struct ta_firmware_header_v1_0 *)adev->psp.ta_fw->data;
		adev->psp.ta_xgmi_ucode_version = le32_to_cpu(ta_hdr->ta_xgmi_ucode_version);
		adev->psp.ta_xgmi_ucode_size = le32_to_cpu(ta_hdr->ta_xgmi_size_bytes);
		adev->psp.ta_xgmi_start_addr = (uint8_t *)ta_hdr +
			le32_to_cpu(ta_hdr->header.ucode_array_offset_bytes);
	}

	return 0;

out2:
	release_firmware(adev->psp.ta_fw);
	adev->psp.ta_fw = NULL;
out1:
	release_firmware(adev->psp.asd_fw);
	adev->psp.asd_fw = NULL;
out:
	dev_err(adev->dev,
		"psp v11.0: Failed to load firmware \"%s\"\n", fw_name);
	release_firmware(adev->psp.sos_fw);
	adev->psp.sos_fw = NULL;

	return err;
}