uartlite.c 17.6 KB
Newer Older
P
Peter Korsgaard 已提交
1 2 3
/*
 * uartlite.c: Serial driver for Xilinx uartlite serial controller
 *
4 5
 * Copyright (C) 2006 Peter Korsgaard <jacmet@sunsite.dk>
 * Copyright (C) 2007 Secret Lab Technologies Ltd.
P
Peter Korsgaard 已提交
6 7 8 9 10 11 12 13 14 15 16 17
 *
 * This file is licensed under the terms of the GNU General Public License
 * version 2.  This program is licensed "as is" without any warranty of any
 * kind, whether express or implied.
 */

#include <linux/platform_device.h>
#include <linux/module.h>
#include <linux/console.h>
#include <linux/serial.h>
#include <linux/serial_core.h>
#include <linux/tty.h>
18
#include <linux/tty_flip.h>
P
Peter Korsgaard 已提交
19 20
#include <linux/delay.h>
#include <linux/interrupt.h>
21
#include <linux/init.h>
22
#include <linux/io.h>
23
#include <linux/of.h>
24
#include <linux/of_address.h>
25 26
#include <linux/of_device.h>
#include <linux/of_platform.h>
27

28
#define ULITE_NAME		"ttyUL"
P
Peter Korsgaard 已提交
29 30
#define ULITE_MAJOR		204
#define ULITE_MINOR		187
31
#define ULITE_NR_UARTS		16
P
Peter Korsgaard 已提交
32

33 34 35 36
/* ---------------------------------------------------------------------
 * Register definitions
 *
 * For register details see datasheet:
37
 * http://www.xilinx.com/support/documentation/ip_documentation/opb_uartlite.pdf
38 39
 */

P
Peter Korsgaard 已提交
40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59
#define ULITE_RX		0x00
#define ULITE_TX		0x04
#define ULITE_STATUS		0x08
#define ULITE_CONTROL		0x0c

#define ULITE_REGION		16

#define ULITE_STATUS_RXVALID	0x01
#define ULITE_STATUS_RXFULL	0x02
#define ULITE_STATUS_TXEMPTY	0x04
#define ULITE_STATUS_TXFULL	0x08
#define ULITE_STATUS_IE		0x10
#define ULITE_STATUS_OVERRUN	0x20
#define ULITE_STATUS_FRAME	0x40
#define ULITE_STATUS_PARITY	0x80

#define ULITE_CONTROL_RST_TX	0x01
#define ULITE_CONTROL_RST_RX	0x02
#define ULITE_CONTROL_IE	0x10

60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107
struct uartlite_reg_ops {
	u32 (*in)(void __iomem *addr);
	void (*out)(u32 val, void __iomem *addr);
};

static u32 uartlite_inbe32(void __iomem *addr)
{
	return ioread32be(addr);
}

static void uartlite_outbe32(u32 val, void __iomem *addr)
{
	iowrite32be(val, addr);
}

static struct uartlite_reg_ops uartlite_be = {
	.in = uartlite_inbe32,
	.out = uartlite_outbe32,
};

static u32 uartlite_inle32(void __iomem *addr)
{
	return ioread32(addr);
}

static void uartlite_outle32(u32 val, void __iomem *addr)
{
	iowrite32(val, addr);
}

static struct uartlite_reg_ops uartlite_le = {
	.in = uartlite_inle32,
	.out = uartlite_outle32,
};

static inline u32 uart_in32(u32 offset, struct uart_port *port)
{
	struct uartlite_reg_ops *reg_ops = port->private_data;

	return reg_ops->in(port->membase + offset);
}

static inline void uart_out32(u32 val, u32 offset, struct uart_port *port)
{
	struct uartlite_reg_ops *reg_ops = port->private_data;

	reg_ops->out(val, port->membase + offset);
}
P
Peter Korsgaard 已提交
108

109
static struct uart_port ulite_ports[ULITE_NR_UARTS];
P
Peter Korsgaard 已提交
110

111 112 113 114
/* ---------------------------------------------------------------------
 * Core UART driver operations
 */

P
Peter Korsgaard 已提交
115 116
static int ulite_receive(struct uart_port *port, int stat)
{
J
Jiri Slaby 已提交
117
	struct tty_port *tport = &port->state->port;
P
Peter Korsgaard 已提交
118 119 120 121 122 123 124 125 126 127
	unsigned char ch = 0;
	char flag = TTY_NORMAL;

	if ((stat & (ULITE_STATUS_RXVALID | ULITE_STATUS_OVERRUN
		     | ULITE_STATUS_FRAME)) == 0)
		return 0;

	/* stats */
	if (stat & ULITE_STATUS_RXVALID) {
		port->icount.rx++;
128
		ch = uart_in32(ULITE_RX, port);
P
Peter Korsgaard 已提交
129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153

		if (stat & ULITE_STATUS_PARITY)
			port->icount.parity++;
	}

	if (stat & ULITE_STATUS_OVERRUN)
		port->icount.overrun++;

	if (stat & ULITE_STATUS_FRAME)
		port->icount.frame++;


	/* drop byte with parity error if IGNPAR specificed */
	if (stat & port->ignore_status_mask & ULITE_STATUS_PARITY)
		stat &= ~ULITE_STATUS_RXVALID;

	stat &= port->read_status_mask;

	if (stat & ULITE_STATUS_PARITY)
		flag = TTY_PARITY;


	stat &= ~port->ignore_status_mask;

	if (stat & ULITE_STATUS_RXVALID)
J
Jiri Slaby 已提交
154
		tty_insert_flip_char(tport, ch, flag);
P
Peter Korsgaard 已提交
155 156

	if (stat & ULITE_STATUS_FRAME)
J
Jiri Slaby 已提交
157
		tty_insert_flip_char(tport, 0, TTY_FRAME);
P
Peter Korsgaard 已提交
158 159

	if (stat & ULITE_STATUS_OVERRUN)
J
Jiri Slaby 已提交
160
		tty_insert_flip_char(tport, 0, TTY_OVERRUN);
P
Peter Korsgaard 已提交
161 162 163 164 165 166

	return 1;
}

static int ulite_transmit(struct uart_port *port, int stat)
{
A
Alan Cox 已提交
167
	struct circ_buf *xmit  = &port->state->xmit;
P
Peter Korsgaard 已提交
168 169 170 171 172

	if (stat & ULITE_STATUS_TXFULL)
		return 0;

	if (port->x_char) {
173
		uart_out32(port->x_char, ULITE_TX, port);
P
Peter Korsgaard 已提交
174 175 176 177 178 179 180 181
		port->x_char = 0;
		port->icount.tx++;
		return 1;
	}

	if (uart_circ_empty(xmit) || uart_tx_stopped(port))
		return 0;

182
	uart_out32(xmit->buf[xmit->tail], ULITE_TX, port);
P
Peter Korsgaard 已提交
183 184 185 186 187 188 189 190 191 192 193 194
	xmit->tail = (xmit->tail + 1) & (UART_XMIT_SIZE-1);
	port->icount.tx++;

	/* wake up */
	if (uart_circ_chars_pending(xmit) < WAKEUP_CHARS)
		uart_write_wakeup(port);

	return 1;
}

static irqreturn_t ulite_isr(int irq, void *dev_id)
{
195
	struct uart_port *port = dev_id;
196
	int busy, n = 0;
197
	unsigned long flags;
P
Peter Korsgaard 已提交
198

199
	spin_lock_irqsave(&port->lock, flags);
P
Peter Korsgaard 已提交
200
	do {
201
		int stat = uart_in32(ULITE_STATUS, port);
P
Peter Korsgaard 已提交
202 203
		busy  = ulite_receive(port, stat);
		busy |= ulite_transmit(port, stat);
204
		n++;
P
Peter Korsgaard 已提交
205 206
	} while (busy);

207 208
	spin_unlock_irqrestore(&port->lock, flags);

209 210
	/* work done? */
	if (n > 1) {
J
Jiri Slaby 已提交
211
		tty_flip_buffer_push(&port->state->port);
212 213 214 215
		return IRQ_HANDLED;
	} else {
		return IRQ_NONE;
	}
P
Peter Korsgaard 已提交
216 217 218 219 220 221 222 223
}

static unsigned int ulite_tx_empty(struct uart_port *port)
{
	unsigned long flags;
	unsigned int ret;

	spin_lock_irqsave(&port->lock, flags);
224
	ret = uart_in32(ULITE_STATUS, port);
P
Peter Korsgaard 已提交
225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246
	spin_unlock_irqrestore(&port->lock, flags);

	return ret & ULITE_STATUS_TXEMPTY ? TIOCSER_TEMT : 0;
}

static unsigned int ulite_get_mctrl(struct uart_port *port)
{
	return TIOCM_CTS | TIOCM_DSR | TIOCM_CAR;
}

static void ulite_set_mctrl(struct uart_port *port, unsigned int mctrl)
{
	/* N/A */
}

static void ulite_stop_tx(struct uart_port *port)
{
	/* N/A */
}

static void ulite_start_tx(struct uart_port *port)
{
247
	ulite_transmit(port, uart_in32(ULITE_STATUS, port));
P
Peter Korsgaard 已提交
248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265
}

static void ulite_stop_rx(struct uart_port *port)
{
	/* don't forward any more data (like !CREAD) */
	port->ignore_status_mask = ULITE_STATUS_RXVALID | ULITE_STATUS_PARITY
		| ULITE_STATUS_FRAME | ULITE_STATUS_OVERRUN;
}

static void ulite_break_ctl(struct uart_port *port, int ctl)
{
	/* N/A */
}

static int ulite_startup(struct uart_port *port)
{
	int ret;

266
	ret = request_irq(port->irq, ulite_isr, IRQF_SHARED, "uartlite", port);
P
Peter Korsgaard 已提交
267 268 269
	if (ret)
		return ret;

270 271 272
	uart_out32(ULITE_CONTROL_RST_RX | ULITE_CONTROL_RST_TX,
		ULITE_CONTROL, port);
	uart_out32(ULITE_CONTROL_IE, ULITE_CONTROL, port);
P
Peter Korsgaard 已提交
273 274 275 276 277 278

	return 0;
}

static void ulite_shutdown(struct uart_port *port)
{
279 280
	uart_out32(0, ULITE_CONTROL, port);
	uart_in32(ULITE_CONTROL, port); /* dummy */
P
Peter Korsgaard 已提交
281 282 283
	free_irq(port->irq, port);
}

A
Alan Cox 已提交
284 285
static void ulite_set_termios(struct uart_port *port, struct ktermios *termios,
			      struct ktermios *old)
P
Peter Korsgaard 已提交
286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325
{
	unsigned long flags;
	unsigned int baud;

	spin_lock_irqsave(&port->lock, flags);

	port->read_status_mask = ULITE_STATUS_RXVALID | ULITE_STATUS_OVERRUN
		| ULITE_STATUS_TXFULL;

	if (termios->c_iflag & INPCK)
		port->read_status_mask |=
			ULITE_STATUS_PARITY | ULITE_STATUS_FRAME;

	port->ignore_status_mask = 0;
	if (termios->c_iflag & IGNPAR)
		port->ignore_status_mask |= ULITE_STATUS_PARITY
			| ULITE_STATUS_FRAME | ULITE_STATUS_OVERRUN;

	/* ignore all characters if CREAD is not set */
	if ((termios->c_cflag & CREAD) == 0)
		port->ignore_status_mask |=
			ULITE_STATUS_RXVALID | ULITE_STATUS_PARITY
			| ULITE_STATUS_FRAME | ULITE_STATUS_OVERRUN;

	/* update timeout */
	baud = uart_get_baud_rate(port, termios, old, 0, 460800);
	uart_update_timeout(port, termios->c_cflag, baud);

	spin_unlock_irqrestore(&port->lock, flags);
}

static const char *ulite_type(struct uart_port *port)
{
	return port->type == PORT_UARTLITE ? "uartlite" : NULL;
}

static void ulite_release_port(struct uart_port *port)
{
	release_mem_region(port->mapbase, ULITE_REGION);
	iounmap(port->membase);
326
	port->membase = NULL;
P
Peter Korsgaard 已提交
327 328 329 330
}

static int ulite_request_port(struct uart_port *port)
{
331 332
	int ret;

333 334
	pr_debug("ulite console: port=%p; port->mapbase=%llx\n",
		 port, (unsigned long long) port->mapbase);
335

P
Peter Korsgaard 已提交
336 337 338 339 340 341 342 343 344 345 346 347
	if (!request_mem_region(port->mapbase, ULITE_REGION, "uartlite")) {
		dev_err(port->dev, "Memory region busy\n");
		return -EBUSY;
	}

	port->membase = ioremap(port->mapbase, ULITE_REGION);
	if (!port->membase) {
		dev_err(port->dev, "Unable to map registers\n");
		release_mem_region(port->mapbase, ULITE_REGION);
		return -EBUSY;
	}

348 349 350 351 352 353 354 355
	port->private_data = &uartlite_be;
	ret = uart_in32(ULITE_CONTROL, port);
	uart_out32(ULITE_CONTROL_RST_TX, ULITE_CONTROL, port);
	ret = uart_in32(ULITE_STATUS, port);
	/* Endianess detection */
	if ((ret & ULITE_STATUS_TXEMPTY) != ULITE_STATUS_TXEMPTY)
		port->private_data = &uartlite_le;

P
Peter Korsgaard 已提交
356 357 358 359 360
	return 0;
}

static void ulite_config_port(struct uart_port *port, int flags)
{
361 362
	if (!ulite_request_port(port))
		port->type = PORT_UARTLITE;
P
Peter Korsgaard 已提交
363 364 365 366 367 368 369 370
}

static int ulite_verify_port(struct uart_port *port, struct serial_struct *ser)
{
	/* we don't want the core code to modify any port params */
	return -EINVAL;
}

371 372 373
#ifdef CONFIG_CONSOLE_POLL
static int ulite_get_poll_char(struct uart_port *port)
{
374
	if (!(uart_in32(ULITE_STATUS, port) & ULITE_STATUS_RXVALID))
375 376
		return NO_POLL_CHAR;

377
	return uart_in32(ULITE_RX, port);
378 379 380 381
}

static void ulite_put_poll_char(struct uart_port *port, unsigned char ch)
{
382
	while (uart_in32(ULITE_STATUS, port) & ULITE_STATUS_TXFULL)
383 384 385
		cpu_relax();

	/* write char to device */
386
	uart_out32(ch, ULITE_TX, port);
387 388 389
}
#endif

P
Peter Korsgaard 已提交
390 391 392 393 394 395 396 397 398 399 400 401 402 403 404
static struct uart_ops ulite_ops = {
	.tx_empty	= ulite_tx_empty,
	.set_mctrl	= ulite_set_mctrl,
	.get_mctrl	= ulite_get_mctrl,
	.stop_tx	= ulite_stop_tx,
	.start_tx	= ulite_start_tx,
	.stop_rx	= ulite_stop_rx,
	.break_ctl	= ulite_break_ctl,
	.startup	= ulite_startup,
	.shutdown	= ulite_shutdown,
	.set_termios	= ulite_set_termios,
	.type		= ulite_type,
	.release_port	= ulite_release_port,
	.request_port	= ulite_request_port,
	.config_port	= ulite_config_port,
405 406 407 408 409
	.verify_port	= ulite_verify_port,
#ifdef CONFIG_CONSOLE_POLL
	.poll_get_char	= ulite_get_poll_char,
	.poll_put_char	= ulite_put_poll_char,
#endif
P
Peter Korsgaard 已提交
410 411
};

412 413 414 415
/* ---------------------------------------------------------------------
 * Console driver operations
 */

P
Peter Korsgaard 已提交
416 417 418
#ifdef CONFIG_SERIAL_UARTLITE_CONSOLE
static void ulite_console_wait_tx(struct uart_port *port)
{
419
	u8 val;
420 421 422 423 424 425 426 427
	unsigned long timeout;

	/*
	 * Spin waiting for TX fifo to have space available.
	 * When using the Microblaze Debug Module this can take up to 1s
	 */
	timeout = jiffies + msecs_to_jiffies(1000);
	while (1) {
428
		val = uart_in32(ULITE_STATUS, port);
429
		if ((val & ULITE_STATUS_TXFULL) == 0)
P
Peter Korsgaard 已提交
430
			break;
431 432 433 434 435
		if (time_after(jiffies, timeout)) {
			dev_warn(port->dev,
				 "timeout waiting for TX buffer empty\n");
			break;
		}
436
		cpu_relax();
P
Peter Korsgaard 已提交
437 438 439 440 441 442
	}
}

static void ulite_console_putchar(struct uart_port *port, int ch)
{
	ulite_console_wait_tx(port);
443
	uart_out32(ch, ULITE_TX, port);
P
Peter Korsgaard 已提交
444 445 446 447 448
}

static void ulite_console_write(struct console *co, const char *s,
				unsigned int count)
{
449
	struct uart_port *port = &ulite_ports[co->index];
P
Peter Korsgaard 已提交
450 451 452 453 454 455 456 457 458 459
	unsigned long flags;
	unsigned int ier;
	int locked = 1;

	if (oops_in_progress) {
		locked = spin_trylock_irqsave(&port->lock, flags);
	} else
		spin_lock_irqsave(&port->lock, flags);

	/* save and disable interrupt */
460 461
	ier = uart_in32(ULITE_STATUS, port) & ULITE_STATUS_IE;
	uart_out32(0, ULITE_CONTROL, port);
P
Peter Korsgaard 已提交
462 463 464 465 466 467 468

	uart_console_write(port, s, count, ulite_console_putchar);

	ulite_console_wait_tx(port);

	/* restore interrupt state */
	if (ier)
469
		uart_out32(ULITE_CONTROL_IE, ULITE_CONTROL, port);
P
Peter Korsgaard 已提交
470 471 472 473 474

	if (locked)
		spin_unlock_irqrestore(&port->lock, flags);
}

B
Bill Pemberton 已提交
475
static int ulite_console_setup(struct console *co, char *options)
P
Peter Korsgaard 已提交
476 477 478 479 480 481 482 483 484 485
{
	struct uart_port *port;
	int baud = 9600;
	int bits = 8;
	int parity = 'n';
	int flow = 'n';

	if (co->index < 0 || co->index >= ULITE_NR_UARTS)
		return -EINVAL;

486
	port = &ulite_ports[co->index];
P
Peter Korsgaard 已提交
487

488
	/* Has the device been initialized yet? */
489 490 491 492 493
	if (!port->mapbase) {
		pr_debug("console on ttyUL%i not present\n", co->index);
		return -ENODEV;
	}

P
Peter Korsgaard 已提交
494
	/* not initialized yet? */
495
	if (!port->membase) {
496 497
		if (ulite_request_port(port))
			return -ENODEV;
498
	}
P
Peter Korsgaard 已提交
499 500 501 502 503 504 505 506 507 508

	if (options)
		uart_parse_options(options, &baud, &parity, &bits, &flow);

	return uart_set_options(port, co, baud, parity, bits, flow);
}

static struct uart_driver ulite_uart_driver;

static struct console ulite_console = {
509
	.name	= ULITE_NAME,
P
Peter Korsgaard 已提交
510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525
	.write	= ulite_console_write,
	.device	= uart_console_device,
	.setup	= ulite_console_setup,
	.flags	= CON_PRINTBUFFER,
	.index	= -1, /* Specified on the cmdline (e.g. console=ttyUL0 ) */
	.data	= &ulite_uart_driver,
};

static int __init ulite_console_init(void)
{
	register_console(&ulite_console);
	return 0;
}

console_initcall(ulite_console_init);

526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566
static void early_uartlite_putc(struct uart_port *port, int c)
{
	/*
	 * Limit how many times we'll spin waiting for TX FIFO status.
	 * This will prevent lockups if the base address is incorrectly
	 * set, or any other issue on the UARTLITE.
	 * This limit is pretty arbitrary, unless we are at about 10 baud
	 * we'll never timeout on a working UART.
	 */

	unsigned retries = 1000000;
	/* read status bit - 0x8 offset */
	while (--retries && (readl(port->membase + 8) & (1 << 3)))
		;

	/* Only attempt the iowrite if we didn't timeout */
	/* write to TX_FIFO - 0x4 offset */
	if (retries)
		writel(c & 0xff, port->membase + 4);
}

static void early_uartlite_write(struct console *console,
				 const char *s, unsigned n)
{
	struct earlycon_device *device = console->data;
	uart_console_write(&device->port, s, n, early_uartlite_putc);
}

static int __init early_uartlite_setup(struct earlycon_device *device,
				       const char *options)
{
	if (!device->port.membase)
		return -ENODEV;

	device->con->write = early_uartlite_write;
	return 0;
}
EARLYCON_DECLARE(uartlite, early_uartlite_setup);
OF_EARLYCON_DECLARE(uartlite_b, "xlnx,opb-uartlite-1.00.b", early_uartlite_setup);
OF_EARLYCON_DECLARE(uartlite_a, "xlnx,xps-uartlite-1.00.a", early_uartlite_setup);

P
Peter Korsgaard 已提交
567 568 569 570 571
#endif /* CONFIG_SERIAL_UARTLITE_CONSOLE */

static struct uart_driver ulite_uart_driver = {
	.owner		= THIS_MODULE,
	.driver_name	= "uartlite",
572
	.dev_name	= ULITE_NAME,
P
Peter Korsgaard 已提交
573 574 575 576 577 578 579 580
	.major		= ULITE_MAJOR,
	.minor		= ULITE_MINOR,
	.nr		= ULITE_NR_UARTS,
#ifdef CONFIG_SERIAL_UARTLITE_CONSOLE
	.cons		= &ulite_console,
#endif
};

581 582 583 584 585 586 587 588 589 590 591 592 593
/* ---------------------------------------------------------------------
 * Port assignment functions (mapping devices to uart_port structures)
 */

/** ulite_assign: register a uartlite device with the driver
 *
 * @dev: pointer to device structure
 * @id: requested id number.  Pass -1 for automatic port assignment
 * @base: base address of uartlite registers
 * @irq: irq number for uartlite
 *
 * Returns: 0 on success, <0 otherwise
 */
B
Bill Pemberton 已提交
594
static int ulite_assign(struct device *dev, int id, u32 base, int irq)
P
Peter Korsgaard 已提交
595 596
{
	struct uart_port *port;
597
	int rc;
P
Peter Korsgaard 已提交
598

599 600 601 602 603 604 605 606
	/* if id = -1; then scan for a free id and use that */
	if (id < 0) {
		for (id = 0; id < ULITE_NR_UARTS; id++)
			if (ulite_ports[id].mapbase == 0)
				break;
	}
	if (id < 0 || id >= ULITE_NR_UARTS) {
		dev_err(dev, "%s%i too large\n", ULITE_NAME, id);
P
Peter Korsgaard 已提交
607
		return -EINVAL;
608
	}
P
Peter Korsgaard 已提交
609

610
	if ((ulite_ports[id].mapbase) && (ulite_ports[id].mapbase != base)) {
611 612
		dev_err(dev, "cannot assign to %s%i; it is already in use\n",
			ULITE_NAME, id);
P
Peter Korsgaard 已提交
613
		return -EBUSY;
614
	}
P
Peter Korsgaard 已提交
615

616
	port = &ulite_ports[id];
P
Peter Korsgaard 已提交
617

618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641
	spin_lock_init(&port->lock);
	port->fifosize = 16;
	port->regshift = 2;
	port->iotype = UPIO_MEM;
	port->iobase = 1; /* mark port in use */
	port->mapbase = base;
	port->membase = NULL;
	port->ops = &ulite_ops;
	port->irq = irq;
	port->flags = UPF_BOOT_AUTOCONF;
	port->dev = dev;
	port->type = PORT_UNKNOWN;
	port->line = id;

	dev_set_drvdata(dev, port);

	/* Register the port */
	rc = uart_add_one_port(&ulite_uart_driver, port);
	if (rc) {
		dev_err(dev, "uart_add_one_port() failed; err=%i\n", rc);
		port->mapbase = 0;
		dev_set_drvdata(dev, NULL);
		return rc;
	}
P
Peter Korsgaard 已提交
642

643 644
	return 0;
}
P
Peter Korsgaard 已提交
645

646 647 648 649
/** ulite_release: register a uartlite device with the driver
 *
 * @dev: pointer to device structure
 */
B
Bill Pemberton 已提交
650
static int ulite_release(struct device *dev)
651 652 653
{
	struct uart_port *port = dev_get_drvdata(dev);
	int rc = 0;
P
Peter Korsgaard 已提交
654

655 656 657 658 659
	if (port) {
		rc = uart_remove_one_port(&ulite_uart_driver, port);
		dev_set_drvdata(dev, NULL);
		port->mapbase = 0;
	}
P
Peter Korsgaard 已提交
660

661
	return rc;
P
Peter Korsgaard 已提交
662 663
}

664 665 666 667
/* ---------------------------------------------------------------------
 * Platform bus binding
 */

668 669
#if defined(CONFIG_OF)
/* Match table for of_platform binding */
670
static const struct of_device_id ulite_of_match[] = {
671 672 673 674 675 676 677
	{ .compatible = "xlnx,opb-uartlite-1.00.b", },
	{ .compatible = "xlnx,xps-uartlite-1.00.a", },
	{}
};
MODULE_DEVICE_TABLE(of, ulite_of_match);
#endif /* CONFIG_OF */

B
Bill Pemberton 已提交
678
static int ulite_probe(struct platform_device *pdev)
P
Peter Korsgaard 已提交
679
{
680 681
	struct resource *res;
	int irq;
682 683 684 685 686 687 688 689
	int id = pdev->id;
#ifdef CONFIG_OF
	const __be32 *prop;

	prop = of_get_property(pdev->dev.of_node, "port-number", NULL);
	if (prop)
		id = be32_to_cpup(prop);
#endif
P
Peter Korsgaard 已提交
690

691 692 693
	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
	if (!res)
		return -ENODEV;
P
Peter Korsgaard 已提交
694

695 696 697
	irq = platform_get_irq(pdev, 0);
	if (irq <= 0)
		return -ENXIO;
P
Peter Korsgaard 已提交
698

699
	return ulite_assign(&pdev->dev, id, res->start, irq);
700
}
P
Peter Korsgaard 已提交
701

B
Bill Pemberton 已提交
702
static int ulite_remove(struct platform_device *pdev)
703 704
{
	return ulite_release(&pdev->dev);
P
Peter Korsgaard 已提交
705 706
}

707 708 709
/* work with hotplug and coldplug */
MODULE_ALIAS("platform:uartlite");

P
Peter Korsgaard 已提交
710
static struct platform_driver ulite_platform_driver = {
711
	.probe = ulite_probe,
712
	.remove = ulite_remove,
713
	.driver = {
714
		.name  = "uartlite",
715
		.of_match_table = of_match_ptr(ulite_of_match),
716 717 718
	},
};

719 720 721 722
/* ---------------------------------------------------------------------
 * Module setup/teardown
 */

723
static int __init ulite_init(void)
P
Peter Korsgaard 已提交
724 725 726
{
	int ret;

727
	pr_debug("uartlite: calling uart_register_driver()\n");
P
Peter Korsgaard 已提交
728 729
	ret = uart_register_driver(&ulite_uart_driver);
	if (ret)
730 731 732
		goto err_uart;

	pr_debug("uartlite: calling platform_driver_register()\n");
P
Peter Korsgaard 已提交
733 734
	ret = platform_driver_register(&ulite_platform_driver);
	if (ret)
735 736 737
		goto err_plat;

	return 0;
P
Peter Korsgaard 已提交
738

739 740 741
err_plat:
	uart_unregister_driver(&ulite_uart_driver);
err_uart:
742
	pr_err("registering uartlite driver failed: err=%i", ret);
P
Peter Korsgaard 已提交
743 744 745
	return ret;
}

746
static void __exit ulite_exit(void)
P
Peter Korsgaard 已提交
747 748 749 750 751 752 753 754 755 756 757
{
	platform_driver_unregister(&ulite_platform_driver);
	uart_unregister_driver(&ulite_uart_driver);
}

module_init(ulite_init);
module_exit(ulite_exit);

MODULE_AUTHOR("Peter Korsgaard <jacmet@sunsite.dk>");
MODULE_DESCRIPTION("Xilinx uartlite serial driver");
MODULE_LICENSE("GPL");