コード例 #1
0
ファイル: ibm_rtl.c プロジェクト: 119-org/hi3518-osdrv
static int ibm_rtl_write(u8 value)
{
	int ret = 0, count = 0;
	static u32 cmd_port_val;

	RTL_DEBUG("%s(%d)\n", __func__, value);

	value = value == 1 ? RTL_CMD_ENTER_PRTM : RTL_CMD_EXIT_PRTM;

	mutex_lock(&rtl_lock);

	if (ioread8(&rtl_table->rt_status) != value) {
		iowrite8(value, &rtl_table->command);

		switch (rtl_cmd_width) {
		case 8:
			cmd_port_val = ioread8(&rtl_table->cmd_port_value);
			RTL_DEBUG("cmd_port_val = %u\n", cmd_port_val);
			iowrite8((u8)cmd_port_val, rtl_cmd_addr);
			break;
		case 16:
			cmd_port_val = ioread16(&rtl_table->cmd_port_value);
			RTL_DEBUG("cmd_port_val = %u\n", cmd_port_val);
			iowrite16((u16)cmd_port_val, rtl_cmd_addr);
			break;
		case 32:
			cmd_port_val = ioread32(&rtl_table->cmd_port_value);
			RTL_DEBUG("cmd_port_val = %u\n", cmd_port_val);
			iowrite32(cmd_port_val, rtl_cmd_addr);
			break;
		}

		while (ioread8(&rtl_table->command)) {
			msleep(10);
			if (count++ > 500) {
				pr_err("Hardware not responding to "
				       "mode switch request\n");
				ret = -EIO;
				break;
			}

		}

		if (ioread8(&rtl_table->command_status)) {
			RTL_DEBUG("command_status reports failed command\n");
			ret = -EIO;
		}
	}

	mutex_unlock(&rtl_lock);
	return ret;
}
コード例 #2
0
ファイル: ibm_rtl.c プロジェクト: 119-org/hi3518-osdrv
static void __exit ibm_rtl_exit(void)
{
	if (rtl_table) {
		RTL_DEBUG("cleaning up");
		/* do not leave the machine in SMI-free mode */
		ibm_rtl_write(0);
		/* unmap, unlink and remove all traces */
		rtl_teardown_sysfs();
		iounmap(ebda_map);
		rtl_port_unmap(rtl_cmd_addr);
	}
}
コード例 #3
0
static void __exit ibm_rtl_exit(void)
{
    if (rtl_table) {
        RTL_DEBUG("cleaning up");

        ibm_rtl_write(0);

        rtl_teardown_sysfs();
        iounmap(ebda_map);
        rtl_port_unmap(rtl_cmd_addr);
    }
}
コード例 #4
0
ファイル: ibm_rtl.c プロジェクト: 119-org/hi3518-osdrv
static int __init ibm_rtl_init(void) {
	unsigned long ebda_addr, ebda_size;
	unsigned int ebda_kb;
	int ret = -ENODEV, i;

	if (force)
		pr_warn("module loaded by force\n");
	/* first ensure that we are running on IBM HW */
	else if (efi_enabled || !dmi_check_system(ibm_rtl_dmi_table))
		return -ENODEV;

	/* Get the address for the Extended BIOS Data Area */
	ebda_addr = get_bios_ebda();
	if (!ebda_addr) {
		RTL_DEBUG("no BIOS EBDA found\n");
		return -ENODEV;
	}

	ebda_map = ioremap(ebda_addr, 4);
	if (!ebda_map)
		return -ENOMEM;

	/* First word in the EDBA is the Size in KB */
	ebda_kb = ioread16(ebda_map);
	RTL_DEBUG("EBDA is %d kB\n", ebda_kb);

	if (ebda_kb == 0)
		goto out;

	iounmap(ebda_map);
	ebda_size = ebda_kb*1024;

	/* Remap the whole table */
	ebda_map = ioremap(ebda_addr, ebda_size);
	if (!ebda_map)
		return -ENOMEM;

	/* search for the _RTL_ signature at the start of the table */
	for (i = 0 ; i < ebda_size/sizeof(unsigned int); i++) {
		struct ibm_rtl_table __iomem * tmp;
		tmp = (struct ibm_rtl_table __iomem *) (ebda_map+i);
		if ((readq(&tmp->signature) & RTL_MASK) == RTL_SIGNATURE) {
			phys_addr_t addr;
			unsigned int plen;
			RTL_DEBUG("found RTL_SIGNATURE at %p\n", tmp);
			rtl_table = tmp;
			/* The address, value, width and offset are platform
			 * dependent and found in the ibm_rtl_table */
			rtl_cmd_width = ioread8(&rtl_table->cmd_granularity);
			rtl_cmd_type = ioread8(&rtl_table->cmd_address_type);
			RTL_DEBUG("rtl_cmd_width = %u, rtl_cmd_type = %u\n",
				  rtl_cmd_width, rtl_cmd_type);
			addr = ioread32(&rtl_table->cmd_port_address);
			RTL_DEBUG("addr = %#llx\n", (unsigned long long)addr);
			plen = rtl_cmd_width/sizeof(char);
			rtl_cmd_addr = rtl_port_map(addr, plen);
			RTL_DEBUG("rtl_cmd_addr = %p\n", rtl_cmd_addr);
			if (!rtl_cmd_addr) {
				ret = -ENOMEM;
				break;
			}
			ret = rtl_setup_sysfs();
			break;
		}
	}

out:
	if (ret) {
		iounmap(ebda_map);
		rtl_port_unmap(rtl_cmd_addr);
	}

	return ret;
}
コード例 #5
0
static int __init ibm_rtl_init(void) {
    unsigned long ebda_addr, ebda_size;
    unsigned int ebda_kb;
    int ret = -ENODEV, i;

    if (force)
        pr_warn("module loaded by force\n");

    else if (efi_enabled || !dmi_check_system(ibm_rtl_dmi_table))
        return -ENODEV;


    ebda_addr = get_bios_ebda();
    if (!ebda_addr) {
        RTL_DEBUG("no BIOS EBDA found\n");
        return -ENODEV;
    }

    ebda_map = ioremap(ebda_addr, 4);
    if (!ebda_map)
        return -ENOMEM;


    ebda_kb = ioread16(ebda_map);
    RTL_DEBUG("EBDA is %d kB\n", ebda_kb);

    if (ebda_kb == 0)
        goto out;

    iounmap(ebda_map);
    ebda_size = ebda_kb*1024;


    ebda_map = ioremap(ebda_addr, ebda_size);
    if (!ebda_map)
        return -ENOMEM;


    for (i = 0 ; i < ebda_size/sizeof(unsigned int); i++) {
        struct ibm_rtl_table __iomem * tmp;
        tmp = (struct ibm_rtl_table __iomem *) (ebda_map+i);
        if ((readq(&tmp->signature) & RTL_MASK) == RTL_SIGNATURE) {
            phys_addr_t addr;
            unsigned int plen;
            RTL_DEBUG("found RTL_SIGNATURE at %p\n", tmp);
            rtl_table = tmp;
            rtl_cmd_width = ioread8(&rtl_table->cmd_granularity);
            rtl_cmd_type = ioread8(&rtl_table->cmd_address_type);
            RTL_DEBUG("rtl_cmd_width = %u, rtl_cmd_type = %u\n",
                      rtl_cmd_width, rtl_cmd_type);
            addr = ioread32(&rtl_table->cmd_port_address);
            RTL_DEBUG("addr = %#llx\n", (unsigned long long)addr);
            plen = rtl_cmd_width/sizeof(char);
            rtl_cmd_addr = rtl_port_map(addr, plen);
            RTL_DEBUG("rtl_cmd_addr = %p\n", rtl_cmd_addr);
            if (!rtl_cmd_addr) {
                ret = -ENOMEM;
                break;
            }
            ret = rtl_setup_sysfs();
            break;
        }
    }

out:
    if (ret) {
        iounmap(ebda_map);
        rtl_port_unmap(rtl_cmd_addr);
    }

    return ret;
}