Linux Audio

Check our new training course

Loading...
v3.1
 
  1/*
  2 * Description:
  3 * Device Driver for the Infineon Technologies
  4 * SLD 9630 TT 1.1 and SLB 9635 TT 1.2 Trusted Platform Module
  5 * Specifications at www.trustedcomputinggroup.org
  6 *
  7 * Copyright (C) 2005, Marcel Selhorst <m.selhorst@sirrix.com>
  8 * Sirrix AG - security technologies, http://www.sirrix.com and
  9 * Applied Data Security Group, Ruhr-University Bochum, Germany
 10 * Project-Homepage: http://www.trust.rub.de/projects/linux-device-driver-infineon-tpm/ 
 11 *
 12 * This program is free software; you can redistribute it and/or
 13 * modify it under the terms of the GNU General Public License as
 14 * published by the Free Software Foundation, version 2 of the
 15 * License.
 16 */
 17
 18#include <linux/init.h>
 19#include <linux/pnp.h>
 20#include "tpm.h"
 21
 22/* Infineon specific definitions */
 23/* maximum number of WTX-packages */
 24#define	TPM_MAX_WTX_PACKAGES 	50
 25/* msleep-Time for WTX-packages */
 26#define	TPM_WTX_MSLEEP_TIME 	20
 27/* msleep-Time --> Interval to check status register */
 28#define	TPM_MSLEEP_TIME 	3
 29/* gives number of max. msleep()-calls before throwing timeout */
 30#define	TPM_MAX_TRIES		5000
 31#define	TPM_INFINEON_DEV_VEN_VALUE	0x15D1
 32
 33#define TPM_INF_IO_PORT		0x0
 34#define TPM_INF_IO_MEM		0x1
 35
 36#define TPM_INF_ADDR		0x0
 37#define TPM_INF_DATA		0x1
 38
 39struct tpm_inf_dev {
 40	int iotype;
 41
 42	void __iomem *mem_base;	/* MMIO ioremap'd addr */
 43	unsigned long map_base;	/* phys MMIO base */
 44	unsigned long map_size;	/* MMIO region size */
 45	unsigned int index_off;	/* index register offset */
 46
 47	unsigned int data_regs;	/* Data registers */
 48	unsigned int data_size;
 49
 50	unsigned int config_port;	/* IO Port config index reg */
 51	unsigned int config_size;
 52};
 53
 54static struct tpm_inf_dev tpm_dev;
 55
 56static inline void tpm_data_out(unsigned char data, unsigned char offset)
 57{
 
 58	if (tpm_dev.iotype == TPM_INF_IO_PORT)
 59		outb(data, tpm_dev.data_regs + offset);
 60	else
 
 61		writeb(data, tpm_dev.mem_base + tpm_dev.data_regs + offset);
 62}
 63
 64static inline unsigned char tpm_data_in(unsigned char offset)
 65{
 
 66	if (tpm_dev.iotype == TPM_INF_IO_PORT)
 67		return inb(tpm_dev.data_regs + offset);
 68	else
 69		return readb(tpm_dev.mem_base + tpm_dev.data_regs + offset);
 70}
 71
 72static inline void tpm_config_out(unsigned char data, unsigned char offset)
 73{
 
 74	if (tpm_dev.iotype == TPM_INF_IO_PORT)
 75		outb(data, tpm_dev.config_port + offset);
 76	else
 
 77		writeb(data, tpm_dev.mem_base + tpm_dev.index_off + offset);
 78}
 79
 80static inline unsigned char tpm_config_in(unsigned char offset)
 81{
 
 82	if (tpm_dev.iotype == TPM_INF_IO_PORT)
 83		return inb(tpm_dev.config_port + offset);
 84	else
 85		return readb(tpm_dev.mem_base + tpm_dev.index_off + offset);
 86}
 87
 88/* TPM header definitions */
 89enum infineon_tpm_header {
 90	TPM_VL_VER = 0x01,
 91	TPM_VL_CHANNEL_CONTROL = 0x07,
 92	TPM_VL_CHANNEL_PERSONALISATION = 0x0A,
 93	TPM_VL_CHANNEL_TPM = 0x0B,
 94	TPM_VL_CONTROL = 0x00,
 95	TPM_INF_NAK = 0x15,
 96	TPM_CTRL_WTX = 0x10,
 97	TPM_CTRL_WTX_ABORT = 0x18,
 98	TPM_CTRL_WTX_ABORT_ACK = 0x18,
 99	TPM_CTRL_ERROR = 0x20,
100	TPM_CTRL_CHAININGACK = 0x40,
101	TPM_CTRL_CHAINING = 0x80,
102	TPM_CTRL_DATA = 0x04,
103	TPM_CTRL_DATA_CHA = 0x84,
104	TPM_CTRL_DATA_CHA_ACK = 0xC4
105};
106
107enum infineon_tpm_register {
108	WRFIFO = 0x00,
109	RDFIFO = 0x01,
110	STAT = 0x02,
111	CMD = 0x03
112};
113
114enum infineon_tpm_command_bits {
115	CMD_DIS = 0x00,
116	CMD_LP = 0x01,
117	CMD_RES = 0x02,
118	CMD_IRQC = 0x06
119};
120
121enum infineon_tpm_status_bits {
122	STAT_XFE = 0x00,
123	STAT_LPA = 0x01,
124	STAT_FOK = 0x02,
125	STAT_TOK = 0x03,
126	STAT_IRQA = 0x06,
127	STAT_RDA = 0x07
128};
129
130/* some outgoing values */
131enum infineon_tpm_values {
132	CHIP_ID1 = 0x20,
133	CHIP_ID2 = 0x21,
134	TPM_DAR = 0x30,
135	RESET_LP_IRQC_DISABLE = 0x41,
136	ENABLE_REGISTER_PAIR = 0x55,
137	IOLIMH = 0x60,
138	IOLIML = 0x61,
139	DISABLE_REGISTER_PAIR = 0xAA,
140	IDVENL = 0xF1,
141	IDVENH = 0xF2,
142	IDPDL = 0xF3,
143	IDPDH = 0xF4
144};
145
146static int number_of_wtx;
147
148static int empty_fifo(struct tpm_chip *chip, int clear_wrfifo)
149{
150	int status;
151	int check = 0;
152	int i;
153
154	if (clear_wrfifo) {
155		for (i = 0; i < 4096; i++) {
156			status = tpm_data_in(WRFIFO);
157			if (status == 0xff) {
158				if (check == 5)
159					break;
160				else
161					check++;
162			}
163		}
164	}
165	/* Note: The values which are currently in the FIFO of the TPM
166	   are thrown away since there is no usage for them. Usually,
167	   this has nothing to say, since the TPM will give its answer
168	   immediately or will be aborted anyway, so the data here is
169	   usually garbage and useless.
170	   We have to clean this, because the next communication with
171	   the TPM would be rubbish, if there is still some old data
172	   in the Read FIFO.
173	 */
174	i = 0;
175	do {
176		status = tpm_data_in(RDFIFO);
177		status = tpm_data_in(STAT);
178		i++;
179		if (i == TPM_MAX_TRIES)
180			return -EIO;
181	} while ((status & (1 << STAT_RDA)) != 0);
182	return 0;
183}
184
185static int wait(struct tpm_chip *chip, int wait_for_bit)
186{
187	int status;
188	int i;
189	for (i = 0; i < TPM_MAX_TRIES; i++) {
190		status = tpm_data_in(STAT);
191		/* check the status-register if wait_for_bit is set */
192		if (status & 1 << wait_for_bit)
193			break;
194		msleep(TPM_MSLEEP_TIME);
195	}
196	if (i == TPM_MAX_TRIES) {	/* timeout occurs */
197		if (wait_for_bit == STAT_XFE)
198			dev_err(chip->dev, "Timeout in wait(STAT_XFE)\n");
199		if (wait_for_bit == STAT_RDA)
200			dev_err(chip->dev, "Timeout in wait(STAT_RDA)\n");
201		return -EIO;
202	}
203	return 0;
204};
205
206static void wait_and_send(struct tpm_chip *chip, u8 sendbyte)
207{
208	wait(chip, STAT_XFE);
209	tpm_data_out(sendbyte, WRFIFO);
210}
211
212    /* Note: WTX means Waiting-Time-Extension. Whenever the TPM needs more
213       calculation time, it sends a WTX-package, which has to be acknowledged
214       or aborted. This usually occurs if you are hammering the TPM with key
215       creation. Set the maximum number of WTX-packages in the definitions
216       above, if the number is reached, the waiting-time will be denied
217       and the TPM command has to be resend.
218     */
219
220static void tpm_wtx(struct tpm_chip *chip)
221{
222	number_of_wtx++;
223	dev_info(chip->dev, "Granting WTX (%02d / %02d)\n",
224		 number_of_wtx, TPM_MAX_WTX_PACKAGES);
225	wait_and_send(chip, TPM_VL_VER);
226	wait_and_send(chip, TPM_CTRL_WTX);
227	wait_and_send(chip, 0x00);
228	wait_and_send(chip, 0x00);
229	msleep(TPM_WTX_MSLEEP_TIME);
230}
231
232static void tpm_wtx_abort(struct tpm_chip *chip)
233{
234	dev_info(chip->dev, "Aborting WTX\n");
235	wait_and_send(chip, TPM_VL_VER);
236	wait_and_send(chip, TPM_CTRL_WTX_ABORT);
237	wait_and_send(chip, 0x00);
238	wait_and_send(chip, 0x00);
239	number_of_wtx = 0;
240	msleep(TPM_WTX_MSLEEP_TIME);
241}
242
243static int tpm_inf_recv(struct tpm_chip *chip, u8 * buf, size_t count)
244{
245	int i;
246	int ret;
247	u32 size = 0;
248	number_of_wtx = 0;
249
250recv_begin:
251	/* start receiving header */
252	for (i = 0; i < 4; i++) {
253		ret = wait(chip, STAT_RDA);
254		if (ret)
255			return -EIO;
256		buf[i] = tpm_data_in(RDFIFO);
257	}
258
259	if (buf[0] != TPM_VL_VER) {
260		dev_err(chip->dev,
261			"Wrong transport protocol implementation!\n");
262		return -EIO;
263	}
264
265	if (buf[1] == TPM_CTRL_DATA) {
266		/* size of the data received */
267		size = ((buf[2] << 8) | buf[3]);
268
269		for (i = 0; i < size; i++) {
270			wait(chip, STAT_RDA);
271			buf[i] = tpm_data_in(RDFIFO);
272		}
273
274		if ((size == 0x6D00) && (buf[1] == 0x80)) {
275			dev_err(chip->dev, "Error handling on vendor layer!\n");
276			return -EIO;
277		}
278
279		for (i = 0; i < size; i++)
280			buf[i] = buf[i + 6];
281
282		size = size - 6;
283		return size;
284	}
285
286	if (buf[1] == TPM_CTRL_WTX) {
287		dev_info(chip->dev, "WTX-package received\n");
288		if (number_of_wtx < TPM_MAX_WTX_PACKAGES) {
289			tpm_wtx(chip);
290			goto recv_begin;
291		} else {
292			tpm_wtx_abort(chip);
293			goto recv_begin;
294		}
295	}
296
297	if (buf[1] == TPM_CTRL_WTX_ABORT_ACK) {
298		dev_info(chip->dev, "WTX-abort acknowledged\n");
299		return size;
300	}
301
302	if (buf[1] == TPM_CTRL_ERROR) {
303		dev_err(chip->dev, "ERROR-package received:\n");
304		if (buf[4] == TPM_INF_NAK)
305			dev_err(chip->dev,
306				"-> Negative acknowledgement"
307				" - retransmit command!\n");
308		return -EIO;
309	}
310	return -EIO;
311}
312
313static int tpm_inf_send(struct tpm_chip *chip, u8 * buf, size_t count)
314{
315	int i;
316	int ret;
317	u8 count_high, count_low, count_4, count_3, count_2, count_1;
318
319	/* Disabling Reset, LP and IRQC */
320	tpm_data_out(RESET_LP_IRQC_DISABLE, CMD);
321
322	ret = empty_fifo(chip, 1);
323	if (ret) {
324		dev_err(chip->dev, "Timeout while clearing FIFO\n");
325		return -EIO;
326	}
327
328	ret = wait(chip, STAT_XFE);
329	if (ret)
330		return -EIO;
331
332	count_4 = (count & 0xff000000) >> 24;
333	count_3 = (count & 0x00ff0000) >> 16;
334	count_2 = (count & 0x0000ff00) >> 8;
335	count_1 = (count & 0x000000ff);
336	count_high = ((count + 6) & 0xffffff00) >> 8;
337	count_low = ((count + 6) & 0x000000ff);
338
339	/* Sending Header */
340	wait_and_send(chip, TPM_VL_VER);
341	wait_and_send(chip, TPM_CTRL_DATA);
342	wait_and_send(chip, count_high);
343	wait_and_send(chip, count_low);
344
345	/* Sending Data Header */
346	wait_and_send(chip, TPM_VL_VER);
347	wait_and_send(chip, TPM_VL_CHANNEL_TPM);
348	wait_and_send(chip, count_4);
349	wait_and_send(chip, count_3);
350	wait_and_send(chip, count_2);
351	wait_and_send(chip, count_1);
352
353	/* Sending Data */
354	for (i = 0; i < count; i++) {
355		wait_and_send(chip, buf[i]);
356	}
357	return count;
358}
359
360static void tpm_inf_cancel(struct tpm_chip *chip)
361{
362	/*
363	   Since we are using the legacy mode to communicate
364	   with the TPM, we have no cancel functions, but have
365	   a workaround for interrupting the TPM through WTX.
366	 */
367}
368
369static u8 tpm_inf_status(struct tpm_chip *chip)
370{
371	return tpm_data_in(STAT);
372}
373
374static DEVICE_ATTR(pubek, S_IRUGO, tpm_show_pubek, NULL);
375static DEVICE_ATTR(pcrs, S_IRUGO, tpm_show_pcrs, NULL);
376static DEVICE_ATTR(caps, S_IRUGO, tpm_show_caps, NULL);
377static DEVICE_ATTR(cancel, S_IWUSR | S_IWGRP, NULL, tpm_store_cancel);
378
379static struct attribute *inf_attrs[] = {
380	&dev_attr_pubek.attr,
381	&dev_attr_pcrs.attr,
382	&dev_attr_caps.attr,
383	&dev_attr_cancel.attr,
384	NULL,
385};
386
387static struct attribute_group inf_attr_grp = {.attrs = inf_attrs };
388
389static const struct file_operations inf_ops = {
390	.owner = THIS_MODULE,
391	.llseek = no_llseek,
392	.open = tpm_open,
393	.read = tpm_read,
394	.write = tpm_write,
395	.release = tpm_release,
396};
397
398static const struct tpm_vendor_specific tpm_inf = {
399	.recv = tpm_inf_recv,
400	.send = tpm_inf_send,
401	.cancel = tpm_inf_cancel,
402	.status = tpm_inf_status,
403	.req_complete_mask = 0,
404	.req_complete_val = 0,
405	.attr_group = &inf_attr_grp,
406	.miscdev = {.fops = &inf_ops,},
407};
408
409static const struct pnp_device_id tpm_inf_pnp_tbl[] = {
410	/* Infineon TPMs */
411	{"IFX0101", 0},
412	{"IFX0102", 0},
413	{"", 0}
414};
415
416MODULE_DEVICE_TABLE(pnp, tpm_inf_pnp_tbl);
417
418static int __devinit tpm_inf_pnp_probe(struct pnp_dev *dev,
419				       const struct pnp_device_id *dev_id)
420{
421	int rc = 0;
422	u8 iol, ioh;
423	int vendorid[2];
424	int version[2];
425	int productid[2];
426	char chipname[20];
427	struct tpm_chip *chip;
428
429	/* read IO-ports through PnP */
430	if (pnp_port_valid(dev, 0) && pnp_port_valid(dev, 1) &&
431	    !(pnp_port_flags(dev, 0) & IORESOURCE_DISABLED)) {
432
433		tpm_dev.iotype = TPM_INF_IO_PORT;
434
435		tpm_dev.config_port = pnp_port_start(dev, 0);
436		tpm_dev.config_size = pnp_port_len(dev, 0);
437		tpm_dev.data_regs = pnp_port_start(dev, 1);
438		tpm_dev.data_size = pnp_port_len(dev, 1);
439		if ((tpm_dev.data_size < 4) || (tpm_dev.config_size < 2)) {
440			rc = -EINVAL;
441			goto err_last;
442		}
443		dev_info(&dev->dev, "Found %s with ID %s\n",
444			 dev->name, dev_id->id);
445		if (!((tpm_dev.data_regs >> 8) & 0xff)) {
446			rc = -EINVAL;
447			goto err_last;
448		}
449		/* publish my base address and request region */
450		if (request_region(tpm_dev.data_regs, tpm_dev.data_size,
451				   "tpm_infineon0") == NULL) {
452			rc = -EINVAL;
453			goto err_last;
454		}
455		if (request_region(tpm_dev.config_port, tpm_dev.config_size,
456				   "tpm_infineon0") == NULL) {
457			release_region(tpm_dev.data_regs, tpm_dev.data_size);
458			rc = -EINVAL;
459			goto err_last;
460		}
461	} else if (pnp_mem_valid(dev, 0) &&
462		   !(pnp_mem_flags(dev, 0) & IORESOURCE_DISABLED)) {
463
464		tpm_dev.iotype = TPM_INF_IO_MEM;
465
466		tpm_dev.map_base = pnp_mem_start(dev, 0);
467		tpm_dev.map_size = pnp_mem_len(dev, 0);
468
469		dev_info(&dev->dev, "Found %s with ID %s\n",
470			 dev->name, dev_id->id);
471
472		/* publish my base address and request region */
473		if (request_mem_region(tpm_dev.map_base, tpm_dev.map_size,
474				       "tpm_infineon0") == NULL) {
475			rc = -EINVAL;
476			goto err_last;
477		}
478
479		tpm_dev.mem_base = ioremap(tpm_dev.map_base, tpm_dev.map_size);
480		if (tpm_dev.mem_base == NULL) {
481			release_mem_region(tpm_dev.map_base, tpm_dev.map_size);
482			rc = -EINVAL;
483			goto err_last;
484		}
485
486		/*
487		 * The only known MMIO based Infineon TPM system provides
488		 * a single large mem region with the device config
489		 * registers at the default TPM_ADDR.  The data registers
490		 * seem like they could be placed anywhere within the MMIO
491		 * region, but lets just put them at zero offset.
492		 */
493		tpm_dev.index_off = TPM_ADDR;
494		tpm_dev.data_regs = 0x0;
495	} else {
496		rc = -EINVAL;
497		goto err_last;
498	}
499
500	/* query chip for its vendor, its version number a.s.o. */
501	tpm_config_out(ENABLE_REGISTER_PAIR, TPM_INF_ADDR);
502	tpm_config_out(IDVENL, TPM_INF_ADDR);
503	vendorid[1] = tpm_config_in(TPM_INF_DATA);
504	tpm_config_out(IDVENH, TPM_INF_ADDR);
505	vendorid[0] = tpm_config_in(TPM_INF_DATA);
506	tpm_config_out(IDPDL, TPM_INF_ADDR);
507	productid[1] = tpm_config_in(TPM_INF_DATA);
508	tpm_config_out(IDPDH, TPM_INF_ADDR);
509	productid[0] = tpm_config_in(TPM_INF_DATA);
510	tpm_config_out(CHIP_ID1, TPM_INF_ADDR);
511	version[1] = tpm_config_in(TPM_INF_DATA);
512	tpm_config_out(CHIP_ID2, TPM_INF_ADDR);
513	version[0] = tpm_config_in(TPM_INF_DATA);
514
515	switch ((productid[0] << 8) | productid[1]) {
516	case 6:
517		snprintf(chipname, sizeof(chipname), " (SLD 9630 TT 1.1)");
518		break;
519	case 11:
520		snprintf(chipname, sizeof(chipname), " (SLB 9635 TT 1.2)");
521		break;
522	default:
523		snprintf(chipname, sizeof(chipname), " (unknown chip)");
524		break;
525	}
526
527	if ((vendorid[0] << 8 | vendorid[1]) == (TPM_INFINEON_DEV_VEN_VALUE)) {
528
529		/* configure TPM with IO-ports */
530		tpm_config_out(IOLIMH, TPM_INF_ADDR);
531		tpm_config_out((tpm_dev.data_regs >> 8) & 0xff, TPM_INF_DATA);
532		tpm_config_out(IOLIML, TPM_INF_ADDR);
533		tpm_config_out((tpm_dev.data_regs & 0xff), TPM_INF_DATA);
534
535		/* control if IO-ports are set correctly */
536		tpm_config_out(IOLIMH, TPM_INF_ADDR);
537		ioh = tpm_config_in(TPM_INF_DATA);
538		tpm_config_out(IOLIML, TPM_INF_ADDR);
539		iol = tpm_config_in(TPM_INF_DATA);
540
541		if ((ioh << 8 | iol) != tpm_dev.data_regs) {
542			dev_err(&dev->dev,
543				"Could not set IO-data registers to 0x%x\n",
544				tpm_dev.data_regs);
545			rc = -EIO;
546			goto err_release_region;
547		}
548
549		/* activate register */
550		tpm_config_out(TPM_DAR, TPM_INF_ADDR);
551		tpm_config_out(0x01, TPM_INF_DATA);
552		tpm_config_out(DISABLE_REGISTER_PAIR, TPM_INF_ADDR);
553
554		/* disable RESET, LP and IRQC */
555		tpm_data_out(RESET_LP_IRQC_DISABLE, CMD);
556
557		/* Finally, we're done, print some infos */
558		dev_info(&dev->dev, "TPM found: "
559			 "config base 0x%lx, "
560			 "data base 0x%lx, "
561			 "chip version 0x%02x%02x, "
562			 "vendor id 0x%x%x (Infineon), "
563			 "product id 0x%02x%02x"
564			 "%s\n",
565			 tpm_dev.iotype == TPM_INF_IO_PORT ?
566			 tpm_dev.config_port :
567			 tpm_dev.map_base + tpm_dev.index_off,
568			 tpm_dev.iotype == TPM_INF_IO_PORT ?
569			 tpm_dev.data_regs :
570			 tpm_dev.map_base + tpm_dev.data_regs,
571			 version[0], version[1],
572			 vendorid[0], vendorid[1],
573			 productid[0], productid[1], chipname);
574
575		if (!(chip = tpm_register_hardware(&dev->dev, &tpm_inf)))
 
 
 
 
 
 
 
576			goto err_release_region;
577
578		return 0;
579	} else {
580		rc = -ENODEV;
581		goto err_release_region;
582	}
583
584err_release_region:
585	if (tpm_dev.iotype == TPM_INF_IO_PORT) {
586		release_region(tpm_dev.data_regs, tpm_dev.data_size);
587		release_region(tpm_dev.config_port, tpm_dev.config_size);
588	} else {
589		iounmap(tpm_dev.mem_base);
590		release_mem_region(tpm_dev.map_base, tpm_dev.map_size);
591	}
592
593err_last:
594	return rc;
595}
596
597static __devexit void tpm_inf_pnp_remove(struct pnp_dev *dev)
598{
599	struct tpm_chip *chip = pnp_get_drvdata(dev);
600
601	if (chip) {
602		if (tpm_dev.iotype == TPM_INF_IO_PORT) {
603			release_region(tpm_dev.data_regs, tpm_dev.data_size);
604			release_region(tpm_dev.config_port,
605				       tpm_dev.config_size);
606		} else {
607			iounmap(tpm_dev.mem_base);
608			release_mem_region(tpm_dev.map_base, tpm_dev.map_size);
609		}
610		tpm_dev_vendor_release(chip);
611		tpm_remove_hardware(chip->dev);
612	}
613}
614
615static int tpm_inf_pnp_suspend(struct pnp_dev *dev, pm_message_t pm_state)
616{
617	struct tpm_chip *chip = pnp_get_drvdata(dev);
618	int rc;
619	if (chip) {
620		u8 savestate[] = {
621			0, 193,	/* TPM_TAG_RQU_COMMAND */
622			0, 0, 0, 10,	/* blob length (in bytes) */
623			0, 0, 0, 152	/* TPM_ORD_SaveState */
624		};
625		dev_info(&dev->dev, "saving TPM state\n");
626		rc = tpm_inf_send(chip, savestate, sizeof(savestate));
627		if (rc < 0) {
628			dev_err(&dev->dev, "error while saving TPM state\n");
629			return rc;
630		}
631	}
632	return 0;
633}
634
635static int tpm_inf_pnp_resume(struct pnp_dev *dev)
 
636{
637	/* Re-configure TPM after suspending */
638	tpm_config_out(ENABLE_REGISTER_PAIR, TPM_INF_ADDR);
639	tpm_config_out(IOLIMH, TPM_INF_ADDR);
640	tpm_config_out((tpm_dev.data_regs >> 8) & 0xff, TPM_INF_DATA);
641	tpm_config_out(IOLIML, TPM_INF_ADDR);
642	tpm_config_out((tpm_dev.data_regs & 0xff), TPM_INF_DATA);
643	/* activate register */
644	tpm_config_out(TPM_DAR, TPM_INF_ADDR);
645	tpm_config_out(0x01, TPM_INF_DATA);
646	tpm_config_out(DISABLE_REGISTER_PAIR, TPM_INF_ADDR);
647	/* disable RESET, LP and IRQC */
648	tpm_data_out(RESET_LP_IRQC_DISABLE, CMD);
649	return tpm_pm_resume(&dev->dev);
650}
 
 
651
652static struct pnp_driver tpm_inf_pnp_driver = {
653	.name = "tpm_inf_pnp",
654	.id_table = tpm_inf_pnp_tbl,
655	.probe = tpm_inf_pnp_probe,
656	.suspend = tpm_inf_pnp_suspend,
657	.resume = tpm_inf_pnp_resume,
658	.remove = __devexit_p(tpm_inf_pnp_remove)
 
659};
660
661static int __init init_inf(void)
662{
663	return pnp_register_driver(&tpm_inf_pnp_driver);
664}
665
666static void __exit cleanup_inf(void)
667{
668	pnp_unregister_driver(&tpm_inf_pnp_driver);
669}
670
671module_init(init_inf);
672module_exit(cleanup_inf);
673
674MODULE_AUTHOR("Marcel Selhorst <m.selhorst@sirrix.com>");
675MODULE_DESCRIPTION("Driver for Infineon TPM SLD 9630 TT 1.1 / SLB 9635 TT 1.2");
676MODULE_VERSION("1.9.2");
677MODULE_LICENSE("GPL");
v6.13.7
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * Description:
  4 * Device Driver for the Infineon Technologies
  5 * SLD 9630 TT 1.1 and SLB 9635 TT 1.2 Trusted Platform Module
  6 * Specifications at www.trustedcomputinggroup.org
  7 *
  8 * Copyright (C) 2005, Marcel Selhorst <tpmdd@selhorst.net>
  9 * Sirrix AG - security technologies <tpmdd@sirrix.com> and
 10 * Applied Data Security Group, Ruhr-University Bochum, Germany
 11 * Project-Homepage: http://www.trust.rub.de/projects/linux-device-driver-infineon-tpm/ 
 
 
 
 
 
 12 */
 13
 14#include <linux/init.h>
 15#include <linux/pnp.h>
 16#include "tpm.h"
 17
 18/* Infineon specific definitions */
 19/* maximum number of WTX-packages */
 20#define	TPM_MAX_WTX_PACKAGES 	50
 21/* msleep-Time for WTX-packages */
 22#define	TPM_WTX_MSLEEP_TIME 	20
 23/* msleep-Time --> Interval to check status register */
 24#define	TPM_MSLEEP_TIME 	3
 25/* gives number of max. msleep()-calls before throwing timeout */
 26#define	TPM_MAX_TRIES		5000
 27#define	TPM_INFINEON_DEV_VEN_VALUE	0x15D1
 28
 29#define TPM_INF_IO_PORT		0x0
 30#define TPM_INF_IO_MEM		0x1
 31
 32#define TPM_INF_ADDR		0x0
 33#define TPM_INF_DATA		0x1
 34
 35struct tpm_inf_dev {
 36	int iotype;
 37
 38	void __iomem *mem_base;	/* MMIO ioremap'd addr */
 39	unsigned long map_base;	/* phys MMIO base */
 40	unsigned long map_size;	/* MMIO region size */
 41	unsigned int index_off;	/* index register offset */
 42
 43	unsigned int data_regs;	/* Data registers */
 44	unsigned int data_size;
 45
 46	unsigned int config_port;	/* IO Port config index reg */
 47	unsigned int config_size;
 48};
 49
 50static struct tpm_inf_dev tpm_dev;
 51
 52static inline void tpm_data_out(unsigned char data, unsigned char offset)
 53{
 54#ifdef CONFIG_HAS_IOPORT
 55	if (tpm_dev.iotype == TPM_INF_IO_PORT)
 56		outb(data, tpm_dev.data_regs + offset);
 57	else
 58#endif
 59		writeb(data, tpm_dev.mem_base + tpm_dev.data_regs + offset);
 60}
 61
 62static inline unsigned char tpm_data_in(unsigned char offset)
 63{
 64#ifdef CONFIG_HAS_IOPORT
 65	if (tpm_dev.iotype == TPM_INF_IO_PORT)
 66		return inb(tpm_dev.data_regs + offset);
 67#endif
 68	return readb(tpm_dev.mem_base + tpm_dev.data_regs + offset);
 69}
 70
 71static inline void tpm_config_out(unsigned char data, unsigned char offset)
 72{
 73#ifdef CONFIG_HAS_IOPORT
 74	if (tpm_dev.iotype == TPM_INF_IO_PORT)
 75		outb(data, tpm_dev.config_port + offset);
 76	else
 77#endif
 78		writeb(data, tpm_dev.mem_base + tpm_dev.index_off + offset);
 79}
 80
 81static inline unsigned char tpm_config_in(unsigned char offset)
 82{
 83#ifdef CONFIG_HAS_IOPORT
 84	if (tpm_dev.iotype == TPM_INF_IO_PORT)
 85		return inb(tpm_dev.config_port + offset);
 86#endif
 87	return readb(tpm_dev.mem_base + tpm_dev.index_off + offset);
 88}
 89
 90/* TPM header definitions */
 91enum infineon_tpm_header {
 92	TPM_VL_VER = 0x01,
 93	TPM_VL_CHANNEL_CONTROL = 0x07,
 94	TPM_VL_CHANNEL_PERSONALISATION = 0x0A,
 95	TPM_VL_CHANNEL_TPM = 0x0B,
 96	TPM_VL_CONTROL = 0x00,
 97	TPM_INF_NAK = 0x15,
 98	TPM_CTRL_WTX = 0x10,
 99	TPM_CTRL_WTX_ABORT = 0x18,
100	TPM_CTRL_WTX_ABORT_ACK = 0x18,
101	TPM_CTRL_ERROR = 0x20,
102	TPM_CTRL_CHAININGACK = 0x40,
103	TPM_CTRL_CHAINING = 0x80,
104	TPM_CTRL_DATA = 0x04,
105	TPM_CTRL_DATA_CHA = 0x84,
106	TPM_CTRL_DATA_CHA_ACK = 0xC4
107};
108
109enum infineon_tpm_register {
110	WRFIFO = 0x00,
111	RDFIFO = 0x01,
112	STAT = 0x02,
113	CMD = 0x03
114};
115
116enum infineon_tpm_command_bits {
117	CMD_DIS = 0x00,
118	CMD_LP = 0x01,
119	CMD_RES = 0x02,
120	CMD_IRQC = 0x06
121};
122
123enum infineon_tpm_status_bits {
124	STAT_XFE = 0x00,
125	STAT_LPA = 0x01,
126	STAT_FOK = 0x02,
127	STAT_TOK = 0x03,
128	STAT_IRQA = 0x06,
129	STAT_RDA = 0x07
130};
131
132/* some outgoing values */
133enum infineon_tpm_values {
134	CHIP_ID1 = 0x20,
135	CHIP_ID2 = 0x21,
136	TPM_DAR = 0x30,
137	RESET_LP_IRQC_DISABLE = 0x41,
138	ENABLE_REGISTER_PAIR = 0x55,
139	IOLIMH = 0x60,
140	IOLIML = 0x61,
141	DISABLE_REGISTER_PAIR = 0xAA,
142	IDVENL = 0xF1,
143	IDVENH = 0xF2,
144	IDPDL = 0xF3,
145	IDPDH = 0xF4
146};
147
148static int number_of_wtx;
149
150static int empty_fifo(struct tpm_chip *chip, int clear_wrfifo)
151{
152	int status;
153	int check = 0;
154	int i;
155
156	if (clear_wrfifo) {
157		for (i = 0; i < 4096; i++) {
158			status = tpm_data_in(WRFIFO);
159			if (status == 0xff) {
160				if (check == 5)
161					break;
162				else
163					check++;
164			}
165		}
166	}
167	/* Note: The values which are currently in the FIFO of the TPM
168	   are thrown away since there is no usage for them. Usually,
169	   this has nothing to say, since the TPM will give its answer
170	   immediately or will be aborted anyway, so the data here is
171	   usually garbage and useless.
172	   We have to clean this, because the next communication with
173	   the TPM would be rubbish, if there is still some old data
174	   in the Read FIFO.
175	 */
176	i = 0;
177	do {
178		status = tpm_data_in(RDFIFO);
179		status = tpm_data_in(STAT);
180		i++;
181		if (i == TPM_MAX_TRIES)
182			return -EIO;
183	} while ((status & (1 << STAT_RDA)) != 0);
184	return 0;
185}
186
187static int wait(struct tpm_chip *chip, int wait_for_bit)
188{
189	int status;
190	int i;
191	for (i = 0; i < TPM_MAX_TRIES; i++) {
192		status = tpm_data_in(STAT);
193		/* check the status-register if wait_for_bit is set */
194		if (status & 1 << wait_for_bit)
195			break;
196		tpm_msleep(TPM_MSLEEP_TIME);
197	}
198	if (i == TPM_MAX_TRIES) {	/* timeout occurs */
199		if (wait_for_bit == STAT_XFE)
200			dev_err(&chip->dev, "Timeout in wait(STAT_XFE)\n");
201		if (wait_for_bit == STAT_RDA)
202			dev_err(&chip->dev, "Timeout in wait(STAT_RDA)\n");
203		return -EIO;
204	}
205	return 0;
206};
207
208static void wait_and_send(struct tpm_chip *chip, u8 sendbyte)
209{
210	wait(chip, STAT_XFE);
211	tpm_data_out(sendbyte, WRFIFO);
212}
213
214    /* Note: WTX means Waiting-Time-Extension. Whenever the TPM needs more
215       calculation time, it sends a WTX-package, which has to be acknowledged
216       or aborted. This usually occurs if you are hammering the TPM with key
217       creation. Set the maximum number of WTX-packages in the definitions
218       above, if the number is reached, the waiting-time will be denied
219       and the TPM command has to be resend.
220     */
221
222static void tpm_wtx(struct tpm_chip *chip)
223{
224	number_of_wtx++;
225	dev_info(&chip->dev, "Granting WTX (%02d / %02d)\n",
226		 number_of_wtx, TPM_MAX_WTX_PACKAGES);
227	wait_and_send(chip, TPM_VL_VER);
228	wait_and_send(chip, TPM_CTRL_WTX);
229	wait_and_send(chip, 0x00);
230	wait_and_send(chip, 0x00);
231	tpm_msleep(TPM_WTX_MSLEEP_TIME);
232}
233
234static void tpm_wtx_abort(struct tpm_chip *chip)
235{
236	dev_info(&chip->dev, "Aborting WTX\n");
237	wait_and_send(chip, TPM_VL_VER);
238	wait_and_send(chip, TPM_CTRL_WTX_ABORT);
239	wait_and_send(chip, 0x00);
240	wait_and_send(chip, 0x00);
241	number_of_wtx = 0;
242	tpm_msleep(TPM_WTX_MSLEEP_TIME);
243}
244
245static int tpm_inf_recv(struct tpm_chip *chip, u8 * buf, size_t count)
246{
247	int i;
248	int ret;
249	u32 size = 0;
250	number_of_wtx = 0;
251
252recv_begin:
253	/* start receiving header */
254	for (i = 0; i < 4; i++) {
255		ret = wait(chip, STAT_RDA);
256		if (ret)
257			return -EIO;
258		buf[i] = tpm_data_in(RDFIFO);
259	}
260
261	if (buf[0] != TPM_VL_VER) {
262		dev_err(&chip->dev,
263			"Wrong transport protocol implementation!\n");
264		return -EIO;
265	}
266
267	if (buf[1] == TPM_CTRL_DATA) {
268		/* size of the data received */
269		size = ((buf[2] << 8) | buf[3]);
270
271		for (i = 0; i < size; i++) {
272			wait(chip, STAT_RDA);
273			buf[i] = tpm_data_in(RDFIFO);
274		}
275
276		if ((size == 0x6D00) && (buf[1] == 0x80)) {
277			dev_err(&chip->dev, "Error handling on vendor layer!\n");
278			return -EIO;
279		}
280
281		for (i = 0; i < size; i++)
282			buf[i] = buf[i + 6];
283
284		size = size - 6;
285		return size;
286	}
287
288	if (buf[1] == TPM_CTRL_WTX) {
289		dev_info(&chip->dev, "WTX-package received\n");
290		if (number_of_wtx < TPM_MAX_WTX_PACKAGES) {
291			tpm_wtx(chip);
292			goto recv_begin;
293		} else {
294			tpm_wtx_abort(chip);
295			goto recv_begin;
296		}
297	}
298
299	if (buf[1] == TPM_CTRL_WTX_ABORT_ACK) {
300		dev_info(&chip->dev, "WTX-abort acknowledged\n");
301		return size;
302	}
303
304	if (buf[1] == TPM_CTRL_ERROR) {
305		dev_err(&chip->dev, "ERROR-package received:\n");
306		if (buf[4] == TPM_INF_NAK)
307			dev_err(&chip->dev,
308				"-> Negative acknowledgement"
309				" - retransmit command!\n");
310		return -EIO;
311	}
312	return -EIO;
313}
314
315static int tpm_inf_send(struct tpm_chip *chip, u8 * buf, size_t count)
316{
317	int i;
318	int ret;
319	u8 count_high, count_low, count_4, count_3, count_2, count_1;
320
321	/* Disabling Reset, LP and IRQC */
322	tpm_data_out(RESET_LP_IRQC_DISABLE, CMD);
323
324	ret = empty_fifo(chip, 1);
325	if (ret) {
326		dev_err(&chip->dev, "Timeout while clearing FIFO\n");
327		return -EIO;
328	}
329
330	ret = wait(chip, STAT_XFE);
331	if (ret)
332		return -EIO;
333
334	count_4 = (count & 0xff000000) >> 24;
335	count_3 = (count & 0x00ff0000) >> 16;
336	count_2 = (count & 0x0000ff00) >> 8;
337	count_1 = (count & 0x000000ff);
338	count_high = ((count + 6) & 0xffffff00) >> 8;
339	count_low = ((count + 6) & 0x000000ff);
340
341	/* Sending Header */
342	wait_and_send(chip, TPM_VL_VER);
343	wait_and_send(chip, TPM_CTRL_DATA);
344	wait_and_send(chip, count_high);
345	wait_and_send(chip, count_low);
346
347	/* Sending Data Header */
348	wait_and_send(chip, TPM_VL_VER);
349	wait_and_send(chip, TPM_VL_CHANNEL_TPM);
350	wait_and_send(chip, count_4);
351	wait_and_send(chip, count_3);
352	wait_and_send(chip, count_2);
353	wait_and_send(chip, count_1);
354
355	/* Sending Data */
356	for (i = 0; i < count; i++) {
357		wait_and_send(chip, buf[i]);
358	}
359	return 0;
360}
361
362static void tpm_inf_cancel(struct tpm_chip *chip)
363{
364	/*
365	   Since we are using the legacy mode to communicate
366	   with the TPM, we have no cancel functions, but have
367	   a workaround for interrupting the TPM through WTX.
368	 */
369}
370
371static u8 tpm_inf_status(struct tpm_chip *chip)
372{
373	return tpm_data_in(STAT);
374}
375
376static const struct tpm_class_ops tpm_inf = {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
377	.recv = tpm_inf_recv,
378	.send = tpm_inf_send,
379	.cancel = tpm_inf_cancel,
380	.status = tpm_inf_status,
381	.req_complete_mask = 0,
382	.req_complete_val = 0,
 
 
383};
384
385static const struct pnp_device_id tpm_inf_pnp_tbl[] = {
386	/* Infineon TPMs */
387	{"IFX0101", 0},
388	{"IFX0102", 0},
389	{"", 0}
390};
391
392MODULE_DEVICE_TABLE(pnp, tpm_inf_pnp_tbl);
393
394static int tpm_inf_pnp_probe(struct pnp_dev *dev,
395				       const struct pnp_device_id *dev_id)
396{
397	int rc = 0;
398	u8 iol, ioh;
399	int vendorid[2];
400	int version[2];
401	int productid[2];
402	const char *chipname;
403	struct tpm_chip *chip;
404
405	/* read IO-ports through PnP */
406	if (pnp_port_valid(dev, 0) && pnp_port_valid(dev, 1) &&
407	    !(pnp_port_flags(dev, 0) & IORESOURCE_DISABLED)) {
408
409		tpm_dev.iotype = TPM_INF_IO_PORT;
410
411		tpm_dev.config_port = pnp_port_start(dev, 0);
412		tpm_dev.config_size = pnp_port_len(dev, 0);
413		tpm_dev.data_regs = pnp_port_start(dev, 1);
414		tpm_dev.data_size = pnp_port_len(dev, 1);
415		if ((tpm_dev.data_size < 4) || (tpm_dev.config_size < 2)) {
416			rc = -EINVAL;
417			goto err_last;
418		}
419		dev_info(&dev->dev, "Found %s with ID %s\n",
420			 dev->name, dev_id->id);
421		if (!((tpm_dev.data_regs >> 8) & 0xff)) {
422			rc = -EINVAL;
423			goto err_last;
424		}
425		/* publish my base address and request region */
426		if (request_region(tpm_dev.data_regs, tpm_dev.data_size,
427				   "tpm_infineon0") == NULL) {
428			rc = -EINVAL;
429			goto err_last;
430		}
431		if (request_region(tpm_dev.config_port, tpm_dev.config_size,
432				   "tpm_infineon0") == NULL) {
433			release_region(tpm_dev.data_regs, tpm_dev.data_size);
434			rc = -EINVAL;
435			goto err_last;
436		}
437	} else if (pnp_mem_valid(dev, 0) &&
438		   !(pnp_mem_flags(dev, 0) & IORESOURCE_DISABLED)) {
439
440		tpm_dev.iotype = TPM_INF_IO_MEM;
441
442		tpm_dev.map_base = pnp_mem_start(dev, 0);
443		tpm_dev.map_size = pnp_mem_len(dev, 0);
444
445		dev_info(&dev->dev, "Found %s with ID %s\n",
446			 dev->name, dev_id->id);
447
448		/* publish my base address and request region */
449		if (request_mem_region(tpm_dev.map_base, tpm_dev.map_size,
450				       "tpm_infineon0") == NULL) {
451			rc = -EINVAL;
452			goto err_last;
453		}
454
455		tpm_dev.mem_base = ioremap(tpm_dev.map_base, tpm_dev.map_size);
456		if (tpm_dev.mem_base == NULL) {
457			release_mem_region(tpm_dev.map_base, tpm_dev.map_size);
458			rc = -EINVAL;
459			goto err_last;
460		}
461
462		/*
463		 * The only known MMIO based Infineon TPM system provides
464		 * a single large mem region with the device config
465		 * registers at the default TPM_ADDR.  The data registers
466		 * seem like they could be placed anywhere within the MMIO
467		 * region, but lets just put them at zero offset.
468		 */
469		tpm_dev.index_off = TPM_ADDR;
470		tpm_dev.data_regs = 0x0;
471	} else {
472		rc = -EINVAL;
473		goto err_last;
474	}
475
476	/* query chip for its vendor, its version number a.s.o. */
477	tpm_config_out(ENABLE_REGISTER_PAIR, TPM_INF_ADDR);
478	tpm_config_out(IDVENL, TPM_INF_ADDR);
479	vendorid[1] = tpm_config_in(TPM_INF_DATA);
480	tpm_config_out(IDVENH, TPM_INF_ADDR);
481	vendorid[0] = tpm_config_in(TPM_INF_DATA);
482	tpm_config_out(IDPDL, TPM_INF_ADDR);
483	productid[1] = tpm_config_in(TPM_INF_DATA);
484	tpm_config_out(IDPDH, TPM_INF_ADDR);
485	productid[0] = tpm_config_in(TPM_INF_DATA);
486	tpm_config_out(CHIP_ID1, TPM_INF_ADDR);
487	version[1] = tpm_config_in(TPM_INF_DATA);
488	tpm_config_out(CHIP_ID2, TPM_INF_ADDR);
489	version[0] = tpm_config_in(TPM_INF_DATA);
490
491	switch ((productid[0] << 8) | productid[1]) {
492	case 6:
493		chipname = " (SLD 9630 TT 1.1)";
494		break;
495	case 11:
496		chipname = " (SLB 9635 TT 1.2)";
497		break;
498	default:
499		chipname = " (unknown chip)";
500		break;
501	}
502
503	if ((vendorid[0] << 8 | vendorid[1]) == (TPM_INFINEON_DEV_VEN_VALUE)) {
504
505		/* configure TPM with IO-ports */
506		tpm_config_out(IOLIMH, TPM_INF_ADDR);
507		tpm_config_out((tpm_dev.data_regs >> 8) & 0xff, TPM_INF_DATA);
508		tpm_config_out(IOLIML, TPM_INF_ADDR);
509		tpm_config_out((tpm_dev.data_regs & 0xff), TPM_INF_DATA);
510
511		/* control if IO-ports are set correctly */
512		tpm_config_out(IOLIMH, TPM_INF_ADDR);
513		ioh = tpm_config_in(TPM_INF_DATA);
514		tpm_config_out(IOLIML, TPM_INF_ADDR);
515		iol = tpm_config_in(TPM_INF_DATA);
516
517		if ((ioh << 8 | iol) != tpm_dev.data_regs) {
518			dev_err(&dev->dev,
519				"Could not set IO-data registers to 0x%x\n",
520				tpm_dev.data_regs);
521			rc = -EIO;
522			goto err_release_region;
523		}
524
525		/* activate register */
526		tpm_config_out(TPM_DAR, TPM_INF_ADDR);
527		tpm_config_out(0x01, TPM_INF_DATA);
528		tpm_config_out(DISABLE_REGISTER_PAIR, TPM_INF_ADDR);
529
530		/* disable RESET, LP and IRQC */
531		tpm_data_out(RESET_LP_IRQC_DISABLE, CMD);
532
533		/* Finally, we're done, print some infos */
534		dev_info(&dev->dev, "TPM found: "
535			 "config base 0x%lx, "
536			 "data base 0x%lx, "
537			 "chip version 0x%02x%02x, "
538			 "vendor id 0x%x%x (Infineon), "
539			 "product id 0x%02x%02x"
540			 "%s\n",
541			 tpm_dev.iotype == TPM_INF_IO_PORT ?
542			 tpm_dev.config_port :
543			 tpm_dev.map_base + tpm_dev.index_off,
544			 tpm_dev.iotype == TPM_INF_IO_PORT ?
545			 tpm_dev.data_regs :
546			 tpm_dev.map_base + tpm_dev.data_regs,
547			 version[0], version[1],
548			 vendorid[0], vendorid[1],
549			 productid[0], productid[1], chipname);
550
551		chip = tpmm_chip_alloc(&dev->dev, &tpm_inf);
552		if (IS_ERR(chip)) {
553			rc = PTR_ERR(chip);
554			goto err_release_region;
555		}
556
557		rc = tpm_chip_register(chip);
558		if (rc)
559			goto err_release_region;
560
561		return 0;
562	} else {
563		rc = -ENODEV;
564		goto err_release_region;
565	}
566
567err_release_region:
568	if (tpm_dev.iotype == TPM_INF_IO_PORT) {
569		release_region(tpm_dev.data_regs, tpm_dev.data_size);
570		release_region(tpm_dev.config_port, tpm_dev.config_size);
571	} else {
572		iounmap(tpm_dev.mem_base);
573		release_mem_region(tpm_dev.map_base, tpm_dev.map_size);
574	}
575
576err_last:
577	return rc;
578}
579
580static void tpm_inf_pnp_remove(struct pnp_dev *dev)
581{
582	struct tpm_chip *chip = pnp_get_drvdata(dev);
583
584	tpm_chip_unregister(chip);
 
 
 
 
 
 
 
 
 
 
 
 
585
586	if (tpm_dev.iotype == TPM_INF_IO_PORT) {
587		release_region(tpm_dev.data_regs, tpm_dev.data_size);
588		release_region(tpm_dev.config_port,
589			       tpm_dev.config_size);
590	} else {
591		iounmap(tpm_dev.mem_base);
592		release_mem_region(tpm_dev.map_base, tpm_dev.map_size);
 
 
 
 
 
 
 
 
 
593	}
 
594}
595
596#ifdef CONFIG_PM_SLEEP
597static int tpm_inf_resume(struct device *dev)
598{
599	/* Re-configure TPM after suspending */
600	tpm_config_out(ENABLE_REGISTER_PAIR, TPM_INF_ADDR);
601	tpm_config_out(IOLIMH, TPM_INF_ADDR);
602	tpm_config_out((tpm_dev.data_regs >> 8) & 0xff, TPM_INF_DATA);
603	tpm_config_out(IOLIML, TPM_INF_ADDR);
604	tpm_config_out((tpm_dev.data_regs & 0xff), TPM_INF_DATA);
605	/* activate register */
606	tpm_config_out(TPM_DAR, TPM_INF_ADDR);
607	tpm_config_out(0x01, TPM_INF_DATA);
608	tpm_config_out(DISABLE_REGISTER_PAIR, TPM_INF_ADDR);
609	/* disable RESET, LP and IRQC */
610	tpm_data_out(RESET_LP_IRQC_DISABLE, CMD);
611	return tpm_pm_resume(dev);
612}
613#endif
614static SIMPLE_DEV_PM_OPS(tpm_inf_pm, tpm_pm_suspend, tpm_inf_resume);
615
616static struct pnp_driver tpm_inf_pnp_driver = {
617	.name = "tpm_inf_pnp",
618	.id_table = tpm_inf_pnp_tbl,
619	.probe = tpm_inf_pnp_probe,
620	.remove = tpm_inf_pnp_remove,
621	.driver = {
622		.pm = &tpm_inf_pm,
623	}
624};
625
626module_pnp_driver(tpm_inf_pnp_driver);
 
 
 
 
 
 
 
 
 
 
 
627
628MODULE_AUTHOR("Marcel Selhorst <tpmdd@sirrix.com>");
629MODULE_DESCRIPTION("Driver for Infineon TPM SLD 9630 TT 1.1 / SLB 9635 TT 1.2");
630MODULE_VERSION("1.9.2");
631MODULE_LICENSE("GPL");