Esempio n. 1
0
int
tpm_tis12_write(struct tpm_softc *sc, void *buf, int len)
{
	u_int8_t *p = buf;
	size_t cnt;
	int rv, r;

#ifdef TPM_DEBUG
	printf("tpm_tis12_write: sc %p buf %p len %d\n", sc, buf, len);
#endif

	if ((rv = tpm_request_locality(sc, 0)) != 0)
		return rv;

	cnt = 0;
	while (cnt < len - 1) {
		for (r = tpm_getburst(sc); r > 0 && cnt < len - 1; r--) {
			bus_space_write_1(sc->sc_bt, sc->sc_bh, TPM_DATA, *p++);
			cnt++;
		}
		if ((rv = tpm_waitfor(sc, TPM_STS_VALID, TPM_READ_TMO, sc))) {
#ifdef TPM_DEBUG
			printf("tpm_tis12_write: failed burst rv %d\n", rv);
#endif
			return rv;
		}
		sc->sc_stat = tpm_status(sc);
		if (!(sc->sc_stat & TPM_STS_DATA_EXPECT)) {
#ifdef TPM_DEBUG
			printf("tpm_tis12_write: failed rv %d stat=%b\n", rv,
			    sc->sc_stat, TPM_STS_BITS);
#endif
			return EIO;
		}
	}

	bus_space_write_1(sc->sc_bt, sc->sc_bh, TPM_DATA, *p++);
	cnt++;

	if ((rv = tpm_waitfor(sc, TPM_STS_VALID, TPM_READ_TMO, sc))) {
#ifdef TPM_DEBUG
		printf("tpm_tis12_write: failed last byte rv %d\n", rv);
#endif
		return rv;
	}
	if ((sc->sc_stat & TPM_STS_DATA_EXPECT) != 0) {
#ifdef TPM_DEBUG
		printf("tpm_tis12_write: failed rv %d stat=%b\n", rv,
		    sc->sc_stat, TPM_STS_BITS);
#endif
		return EIO;
	}

#ifdef TPM_DEBUG
	printf("tpm_tis12_write: wrote %d byte\n", cnt);
#endif

	return 0;
}
Esempio n. 2
0
/* Start transaction. */
int
tpm_tis12_start(struct tpm_softc *sc, int flag)
{
	int rv;

	if (flag == UIO_READ) {
		rv = tpm_waitfor(sc, TPM_STS_DATA_AVAIL | TPM_STS_VALID,
		    TPM_READ_TMO, sc->sc_read);
		return rv;
	}

	/* Own our (0th) locality. */
	if ((rv = tpm_request_locality(sc, 0)) != 0)
		return rv;

	sc->sc_stat = tpm_status(sc);
	if (sc->sc_stat & TPM_STS_CMD_READY) {
#ifdef TPM_DEBUG
		char buf[128];
		snprintb(buf, sizeof(buf), TPM_STS_BITS, sc->sc_stat);
		aprint_debug_dev(sc->sc_dev, "%s: UIO_WRITE status %s\n",
		    __func__, buf);
#endif
		return 0;
	}

#ifdef TPM_DEBUG
	aprint_debug_dev(sc->sc_dev,
	    "%s: UIO_WRITE readying chip\n", __func__);
#endif

	/* Abort previous and restart. */
	bus_space_write_1(sc->sc_bt, sc->sc_bh, TPM_STS, TPM_STS_CMD_READY);
	if ((rv = tpm_waitfor(sc, TPM_STS_CMD_READY, TPM_READY_TMO,
	    sc->sc_write))) {
#ifdef TPM_DEBUG
		aprint_debug_dev(sc->sc_dev,
		    "%s: UIO_WRITE readying failed %d\n", __func__, rv);
#endif
		return rv;
	}

#ifdef TPM_DEBUG
	aprint_debug_dev(sc->sc_dev,
	    "%s: UIO_WRITE readying done\n", __func__);
#endif

	return 0;
}
Esempio n. 3
0
/* Setup TPM using TIS 1.2 interface. */
int
tpm_tis12_init(struct tpm_softc *sc, int irq, const char *name)
{
	uint32_t r;
	int i;

	r = bus_space_read_4(sc->sc_bt, sc->sc_bh, TPM_INTF_CAPABILITIES);
#ifdef TPM_DEBUG
	char cbuf[128];
	snprintb(cbuf, sizeof(cbuf), TPM_CAPBITS, r);
	aprint_debug_dev(sc->sc_dev, "%s: caps=%s ", __func__, cbuf);
#endif
	if ((r & TPM_CAPSREQ) != TPM_CAPSREQ ||
	    !(r & (TPM_INTF_INT_EDGE_RISING | TPM_INTF_INT_LEVEL_LOW))) {
		char buf[128];
		snprintb(buf, sizeof(buf), TPM_CAPBITS, r);
		aprint_error_dev(sc->sc_dev, "capabilities too low (caps=%s)\n",
		    buf);
		return 1;
	}
	sc->sc_capabilities = r;

	sc->sc_devid = bus_space_read_4(sc->sc_bt, sc->sc_bh, TPM_ID);
	sc->sc_rev = bus_space_read_1(sc->sc_bt, sc->sc_bh, TPM_REV);

	for (i = 0; tpm_devs[i].devid; i++)
		if (tpm_devs[i].devid == sc->sc_devid)
			break;

	if (tpm_devs[i].devid)
		aprint_normal(": %s rev 0x%x\n",
		    tpm_devs[i].name, sc->sc_rev);
	else
		aprint_normal(": device 0x%08x rev 0x%x\n",
		    sc->sc_devid, sc->sc_rev);

	if (tpm_tis12_irqinit(sc, irq, i))
		return 1;

	if (tpm_request_locality(sc, 0))
		return 1;

	/* Abort whatever it thought it was doing. */
	bus_space_write_1(sc->sc_bt, sc->sc_bh, TPM_STS, TPM_STS_CMD_READY);

	return 0;
}
Esempio n. 4
0
/* Start transaction. */
int
tpm_tis12_start(struct tpm_softc *sc, int flag)
{
	int rv;

	if (flag == UIO_READ) {
		rv = tpm_waitfor(sc, TPM_STS_DATA_AVAIL | TPM_STS_VALID,
		    TPM_READ_TMO, sc->sc_read);
		return rv;
	}

	/* Own our (0th) locality. */
	if ((rv = tpm_request_locality(sc, 0)) != 0)
		return rv;

	sc->sc_stat = tpm_status(sc);
	if (sc->sc_stat & TPM_STS_CMD_READY) {
#ifdef TPM_DEBUG
		printf("tpm_tis12_start: UIO_WRITE status %b\n", sc->sc_stat,
		   TPM_STS_BITS);
#endif
		return 0;
	}

#ifdef TPM_DEBUG
	printf("tpm_tis12_start: UIO_WRITE readying chip\n");
#endif

	/* Abort previous and restart. */
	bus_space_write_1(sc->sc_bt, sc->sc_bh, TPM_STS, TPM_STS_CMD_READY);
	if ((rv = tpm_waitfor(sc, TPM_STS_CMD_READY, TPM_READY_TMO,
	    sc->sc_write))) {
#ifdef TPM_DEBUG
		printf("tpm_tis12_start: UIO_WRITE readying failed %d\n", rv);
#endif
		return rv;
	}

#ifdef TPM_DEBUG
	printf("tpm_tis12_start: UIO_WRITE readying done\n");
#endif

	return 0;
}
Esempio n. 5
0
/* Setup TPM using TIS 1.2 interface. */
int
tpm_tis12_init(struct tpm_softc *sc, int irq, const char *name)
{
	u_int32_t r;
	int i;

	r = bus_space_read_4(sc->sc_bt, sc->sc_bh, TPM_INTF_CAPABILITIES);
#ifdef TPM_DEBUG
	printf(" caps=%b ", r, TPM_CAPBITS);
#endif
	if ((r & TPM_CAPSREQ) != TPM_CAPSREQ ||
	    !(r & (TPM_INTF_INT_EDGE_RISING | TPM_INTF_INT_LEVEL_LOW))) {
		printf(": capabilities too low (caps=%b)\n", r, TPM_CAPBITS);
		return 1;
	}
	sc->sc_capabilities = r;

	sc->sc_devid = bus_space_read_4(sc->sc_bt, sc->sc_bh, TPM_ID);
	sc->sc_rev = bus_space_read_1(sc->sc_bt, sc->sc_bh, TPM_REV);

	for (i = 0; tpm_devs[i].devid; i++)
		if (tpm_devs[i].devid == sc->sc_devid)
			break;

	if (tpm_devs[i].devid)
		printf(": %s rev 0x%x\n", tpm_devs[i].name, sc->sc_rev);
	else
		printf(": device 0x%08x rev 0x%x\n", sc->sc_devid, sc->sc_rev);

	if (tpm_tis12_irqinit(sc, irq, i))
		return 1;

	if (tpm_request_locality(sc, 0))
		return 1;

	/* Abort whatever it thought it was doing. */
	bus_space_write_1(sc->sc_bt, sc->sc_bh, TPM_STS, TPM_STS_CMD_READY);

	return 0;
}
Esempio n. 6
0
int
tpm_tis12_write(struct tpm_softc *sc, const void *buf, size_t len)
{
	const uint8_t *p = buf;
	size_t cnt;
	int rv, r;

#ifdef TPM_DEBUG
	aprint_debug_dev(sc->sc_dev,
	    "%s: sc %p buf %p len %zu\n", __func__, sc, buf, len);
#endif
	if (len == 0)
		return 0;

	if ((rv = tpm_request_locality(sc, 0)) != 0)
		return rv;

	cnt = 0;
	while (cnt < len - 1) {
		for (r = tpm_getburst(sc); r > 0 && cnt < len - 1; r--) {
			bus_space_write_1(sc->sc_bt, sc->sc_bh, TPM_DATA, *p++);
			cnt++;
		}
		if ((rv = tpm_waitfor(sc, TPM_STS_VALID, TPM_READ_TMO, sc))) {
#ifdef TPM_DEBUG
			aprint_debug_dev(sc->sc_dev,
			    "%s: failed burst rv %d\n", __func__, rv);
#endif
			return rv;
		}
		sc->sc_stat = tpm_status(sc);
		if (!(sc->sc_stat & TPM_STS_DATA_EXPECT)) {
#ifdef TPM_DEBUG
			char sbuf[128];
			snprintb(sbuf, sizeof(sbuf), TPM_STS_BITS, sc->sc_stat);
			aprint_debug_dev(sc->sc_dev,
			    "%s: failed rv %d stat=%s\n", __func__, rv, sbuf);
#endif
			return EIO;
		}
	}

	bus_space_write_1(sc->sc_bt, sc->sc_bh, TPM_DATA, *p++);
	cnt++;

	if ((rv = tpm_waitfor(sc, TPM_STS_VALID, TPM_READ_TMO, sc))) {
#ifdef TPM_DEBUG
		aprint_debug_dev(sc->sc_dev, "%s: failed last byte rv %d\n",
		    __func__, rv);
#endif
		return rv;
	}
	if ((sc->sc_stat & TPM_STS_DATA_EXPECT) != 0) {
#ifdef TPM_DEBUG
		char sbuf[128];
		snprintb(sbuf, sizeof(sbuf), TPM_STS_BITS, sc->sc_stat);
		aprint_debug_dev(sc->sc_dev,
		    "%s: failed rv %d stat=%s\n", __func__, rv, sbuf);
#endif
		return EIO;
	}

#ifdef TPM_DEBUG
	aprint_debug_dev(sc->sc_dev, "%s: wrote %zu byte\n", __func__, cnt);
#endif

	return 0;
}