162306a36Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0
262306a36Sopenharmony_ci/* ELM327 based CAN interface driver (tty line discipline)
362306a36Sopenharmony_ci *
462306a36Sopenharmony_ci * This driver started as a derivative of linux/drivers/net/can/slcan.c
562306a36Sopenharmony_ci * and my thanks go to the original authors for their inspiration.
662306a36Sopenharmony_ci *
762306a36Sopenharmony_ci * can327.c Author : Max Staudt <max-linux@enpas.org>
862306a36Sopenharmony_ci * slcan.c Author  : Oliver Hartkopp <socketcan@hartkopp.net>
962306a36Sopenharmony_ci * slip.c Authors  : Laurence Culhane <loz@holmes.demon.co.uk>
1062306a36Sopenharmony_ci *                   Fred N. van Kempen <waltje@uwalt.nl.mugnet.org>
1162306a36Sopenharmony_ci */
1262306a36Sopenharmony_ci
1362306a36Sopenharmony_ci#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
1462306a36Sopenharmony_ci
1562306a36Sopenharmony_ci#include <linux/init.h>
1662306a36Sopenharmony_ci#include <linux/module.h>
1762306a36Sopenharmony_ci
1862306a36Sopenharmony_ci#include <linux/bitops.h>
1962306a36Sopenharmony_ci#include <linux/ctype.h>
2062306a36Sopenharmony_ci#include <linux/errno.h>
2162306a36Sopenharmony_ci#include <linux/kernel.h>
2262306a36Sopenharmony_ci#include <linux/list.h>
2362306a36Sopenharmony_ci#include <linux/lockdep.h>
2462306a36Sopenharmony_ci#include <linux/netdevice.h>
2562306a36Sopenharmony_ci#include <linux/skbuff.h>
2662306a36Sopenharmony_ci#include <linux/spinlock.h>
2762306a36Sopenharmony_ci#include <linux/string.h>
2862306a36Sopenharmony_ci#include <linux/tty.h>
2962306a36Sopenharmony_ci#include <linux/tty_ldisc.h>
3062306a36Sopenharmony_ci#include <linux/workqueue.h>
3162306a36Sopenharmony_ci
3262306a36Sopenharmony_ci#include <uapi/linux/tty.h>
3362306a36Sopenharmony_ci
3462306a36Sopenharmony_ci#include <linux/can.h>
3562306a36Sopenharmony_ci#include <linux/can/dev.h>
3662306a36Sopenharmony_ci#include <linux/can/error.h>
3762306a36Sopenharmony_ci#include <linux/can/rx-offload.h>
3862306a36Sopenharmony_ci
3962306a36Sopenharmony_ci#define CAN327_NAPI_WEIGHT 4
4062306a36Sopenharmony_ci
4162306a36Sopenharmony_ci#define CAN327_SIZE_TXBUF 32
4262306a36Sopenharmony_ci#define CAN327_SIZE_RXBUF 1024
4362306a36Sopenharmony_ci
4462306a36Sopenharmony_ci#define CAN327_CAN_CONFIG_SEND_SFF 0x8000
4562306a36Sopenharmony_ci#define CAN327_CAN_CONFIG_VARIABLE_DLC 0x4000
4662306a36Sopenharmony_ci#define CAN327_CAN_CONFIG_RECV_BOTH_SFF_EFF 0x2000
4762306a36Sopenharmony_ci#define CAN327_CAN_CONFIG_BAUDRATE_MULT_8_7 0x1000
4862306a36Sopenharmony_ci
4962306a36Sopenharmony_ci#define CAN327_DUMMY_CHAR 'y'
5062306a36Sopenharmony_ci#define CAN327_DUMMY_STRING "y"
5162306a36Sopenharmony_ci#define CAN327_READY_CHAR '>'
5262306a36Sopenharmony_ci
5362306a36Sopenharmony_ci/* Bits in elm->cmds_todo */
5462306a36Sopenharmony_cienum can327_tx_do {
5562306a36Sopenharmony_ci	CAN327_TX_DO_CAN_DATA = 0,
5662306a36Sopenharmony_ci	CAN327_TX_DO_CANID_11BIT,
5762306a36Sopenharmony_ci	CAN327_TX_DO_CANID_29BIT_LOW,
5862306a36Sopenharmony_ci	CAN327_TX_DO_CANID_29BIT_HIGH,
5962306a36Sopenharmony_ci	CAN327_TX_DO_CAN_CONFIG_PART2,
6062306a36Sopenharmony_ci	CAN327_TX_DO_CAN_CONFIG,
6162306a36Sopenharmony_ci	CAN327_TX_DO_RESPONSES,
6262306a36Sopenharmony_ci	CAN327_TX_DO_SILENT_MONITOR,
6362306a36Sopenharmony_ci	CAN327_TX_DO_INIT,
6462306a36Sopenharmony_ci};
6562306a36Sopenharmony_ci
6662306a36Sopenharmony_cistruct can327 {
6762306a36Sopenharmony_ci	/* This must be the first member when using alloc_candev() */
6862306a36Sopenharmony_ci	struct can_priv can;
6962306a36Sopenharmony_ci
7062306a36Sopenharmony_ci	struct can_rx_offload offload;
7162306a36Sopenharmony_ci
7262306a36Sopenharmony_ci	/* TTY buffers */
7362306a36Sopenharmony_ci	u8 txbuf[CAN327_SIZE_TXBUF];
7462306a36Sopenharmony_ci	u8 rxbuf[CAN327_SIZE_RXBUF];
7562306a36Sopenharmony_ci
7662306a36Sopenharmony_ci	/* Per-channel lock */
7762306a36Sopenharmony_ci	spinlock_t lock;
7862306a36Sopenharmony_ci
7962306a36Sopenharmony_ci	/* TTY and netdev devices that we're bridging */
8062306a36Sopenharmony_ci	struct tty_struct *tty;
8162306a36Sopenharmony_ci	struct net_device *dev;
8262306a36Sopenharmony_ci
8362306a36Sopenharmony_ci	/* TTY buffer accounting */
8462306a36Sopenharmony_ci	struct work_struct tx_work;	/* Flushes TTY TX buffer */
8562306a36Sopenharmony_ci	u8 *txhead;			/* Next TX byte */
8662306a36Sopenharmony_ci	size_t txleft;			/* Bytes left to TX */
8762306a36Sopenharmony_ci	int rxfill;			/* Bytes already RX'd in buffer */
8862306a36Sopenharmony_ci
8962306a36Sopenharmony_ci	/* State machine */
9062306a36Sopenharmony_ci	enum {
9162306a36Sopenharmony_ci		CAN327_STATE_NOTINIT = 0,
9262306a36Sopenharmony_ci		CAN327_STATE_GETDUMMYCHAR,
9362306a36Sopenharmony_ci		CAN327_STATE_GETPROMPT,
9462306a36Sopenharmony_ci		CAN327_STATE_RECEIVING,
9562306a36Sopenharmony_ci	} state;
9662306a36Sopenharmony_ci
9762306a36Sopenharmony_ci	/* Things we have yet to send */
9862306a36Sopenharmony_ci	char **next_init_cmd;
9962306a36Sopenharmony_ci	unsigned long cmds_todo;
10062306a36Sopenharmony_ci
10162306a36Sopenharmony_ci	/* The CAN frame and config the ELM327 is sending/using,
10262306a36Sopenharmony_ci	 * or will send/use after finishing all cmds_todo
10362306a36Sopenharmony_ci	 */
10462306a36Sopenharmony_ci	struct can_frame can_frame_to_send;
10562306a36Sopenharmony_ci	u16 can_config;
10662306a36Sopenharmony_ci	u8 can_bitrate_divisor;
10762306a36Sopenharmony_ci
10862306a36Sopenharmony_ci	/* Parser state */
10962306a36Sopenharmony_ci	bool drop_next_line;
11062306a36Sopenharmony_ci
11162306a36Sopenharmony_ci	/* Stop the channel on UART side hardware failure, e.g. stray
11262306a36Sopenharmony_ci	 * characters or neverending lines. This may be caused by bad
11362306a36Sopenharmony_ci	 * UART wiring, a bad ELM327, a bad UART bridge...
11462306a36Sopenharmony_ci	 * Once this is true, nothing will be sent to the TTY.
11562306a36Sopenharmony_ci	 */
11662306a36Sopenharmony_ci	bool uart_side_failure;
11762306a36Sopenharmony_ci};
11862306a36Sopenharmony_ci
11962306a36Sopenharmony_cistatic inline void can327_uart_side_failure(struct can327 *elm);
12062306a36Sopenharmony_ci
12162306a36Sopenharmony_cistatic void can327_send(struct can327 *elm, const void *buf, size_t len)
12262306a36Sopenharmony_ci{
12362306a36Sopenharmony_ci	int written;
12462306a36Sopenharmony_ci
12562306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
12662306a36Sopenharmony_ci
12762306a36Sopenharmony_ci	if (elm->uart_side_failure)
12862306a36Sopenharmony_ci		return;
12962306a36Sopenharmony_ci
13062306a36Sopenharmony_ci	memcpy(elm->txbuf, buf, len);
13162306a36Sopenharmony_ci
13262306a36Sopenharmony_ci	/* Order of next two lines is *very* important.
13362306a36Sopenharmony_ci	 * When we are sending a little amount of data,
13462306a36Sopenharmony_ci	 * the transfer may be completed inside the ops->write()
13562306a36Sopenharmony_ci	 * routine, because it's running with interrupts enabled.
13662306a36Sopenharmony_ci	 * In this case we *never* got WRITE_WAKEUP event,
13762306a36Sopenharmony_ci	 * if we did not request it before write operation.
13862306a36Sopenharmony_ci	 *       14 Oct 1994  Dmitry Gorodchanin.
13962306a36Sopenharmony_ci	 */
14062306a36Sopenharmony_ci	set_bit(TTY_DO_WRITE_WAKEUP, &elm->tty->flags);
14162306a36Sopenharmony_ci	written = elm->tty->ops->write(elm->tty, elm->txbuf, len);
14262306a36Sopenharmony_ci	if (written < 0) {
14362306a36Sopenharmony_ci		netdev_err(elm->dev, "Failed to write to tty %s.\n",
14462306a36Sopenharmony_ci			   elm->tty->name);
14562306a36Sopenharmony_ci		can327_uart_side_failure(elm);
14662306a36Sopenharmony_ci		return;
14762306a36Sopenharmony_ci	}
14862306a36Sopenharmony_ci
14962306a36Sopenharmony_ci	elm->txleft = len - written;
15062306a36Sopenharmony_ci	elm->txhead = elm->txbuf + written;
15162306a36Sopenharmony_ci}
15262306a36Sopenharmony_ci
15362306a36Sopenharmony_ci/* Take the ELM327 out of almost any state and back into command mode.
15462306a36Sopenharmony_ci * We send CAN327_DUMMY_CHAR which will either abort any running
15562306a36Sopenharmony_ci * operation, or be echoed back to us in case we're already in command
15662306a36Sopenharmony_ci * mode.
15762306a36Sopenharmony_ci */
15862306a36Sopenharmony_cistatic void can327_kick_into_cmd_mode(struct can327 *elm)
15962306a36Sopenharmony_ci{
16062306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
16162306a36Sopenharmony_ci
16262306a36Sopenharmony_ci	if (elm->state != CAN327_STATE_GETDUMMYCHAR &&
16362306a36Sopenharmony_ci	    elm->state != CAN327_STATE_GETPROMPT) {
16462306a36Sopenharmony_ci		can327_send(elm, CAN327_DUMMY_STRING, 1);
16562306a36Sopenharmony_ci
16662306a36Sopenharmony_ci		elm->state = CAN327_STATE_GETDUMMYCHAR;
16762306a36Sopenharmony_ci	}
16862306a36Sopenharmony_ci}
16962306a36Sopenharmony_ci
17062306a36Sopenharmony_ci/* Schedule a CAN frame and necessary config changes to be sent to the TTY. */
17162306a36Sopenharmony_cistatic void can327_send_frame(struct can327 *elm, struct can_frame *frame)
17262306a36Sopenharmony_ci{
17362306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
17462306a36Sopenharmony_ci
17562306a36Sopenharmony_ci	/* Schedule any necessary changes in ELM327's CAN configuration */
17662306a36Sopenharmony_ci	if (elm->can_frame_to_send.can_id != frame->can_id) {
17762306a36Sopenharmony_ci		/* Set the new CAN ID for transmission. */
17862306a36Sopenharmony_ci		if ((frame->can_id ^ elm->can_frame_to_send.can_id)
17962306a36Sopenharmony_ci		    & CAN_EFF_FLAG) {
18062306a36Sopenharmony_ci			elm->can_config =
18162306a36Sopenharmony_ci				(frame->can_id & CAN_EFF_FLAG ? 0 : CAN327_CAN_CONFIG_SEND_SFF) |
18262306a36Sopenharmony_ci				CAN327_CAN_CONFIG_VARIABLE_DLC |
18362306a36Sopenharmony_ci				CAN327_CAN_CONFIG_RECV_BOTH_SFF_EFF |
18462306a36Sopenharmony_ci				elm->can_bitrate_divisor;
18562306a36Sopenharmony_ci
18662306a36Sopenharmony_ci			set_bit(CAN327_TX_DO_CAN_CONFIG, &elm->cmds_todo);
18762306a36Sopenharmony_ci		}
18862306a36Sopenharmony_ci
18962306a36Sopenharmony_ci		if (frame->can_id & CAN_EFF_FLAG) {
19062306a36Sopenharmony_ci			clear_bit(CAN327_TX_DO_CANID_11BIT, &elm->cmds_todo);
19162306a36Sopenharmony_ci			set_bit(CAN327_TX_DO_CANID_29BIT_LOW, &elm->cmds_todo);
19262306a36Sopenharmony_ci			set_bit(CAN327_TX_DO_CANID_29BIT_HIGH, &elm->cmds_todo);
19362306a36Sopenharmony_ci		} else {
19462306a36Sopenharmony_ci			set_bit(CAN327_TX_DO_CANID_11BIT, &elm->cmds_todo);
19562306a36Sopenharmony_ci			clear_bit(CAN327_TX_DO_CANID_29BIT_LOW,
19662306a36Sopenharmony_ci				  &elm->cmds_todo);
19762306a36Sopenharmony_ci			clear_bit(CAN327_TX_DO_CANID_29BIT_HIGH,
19862306a36Sopenharmony_ci				  &elm->cmds_todo);
19962306a36Sopenharmony_ci		}
20062306a36Sopenharmony_ci	}
20162306a36Sopenharmony_ci
20262306a36Sopenharmony_ci	/* Schedule the CAN frame itself. */
20362306a36Sopenharmony_ci	elm->can_frame_to_send = *frame;
20462306a36Sopenharmony_ci	set_bit(CAN327_TX_DO_CAN_DATA, &elm->cmds_todo);
20562306a36Sopenharmony_ci
20662306a36Sopenharmony_ci	can327_kick_into_cmd_mode(elm);
20762306a36Sopenharmony_ci}
20862306a36Sopenharmony_ci
20962306a36Sopenharmony_ci/* ELM327 initialisation sequence.
21062306a36Sopenharmony_ci * The line length is limited by the buffer in can327_handle_prompt().
21162306a36Sopenharmony_ci */
21262306a36Sopenharmony_cistatic char *can327_init_script[] = {
21362306a36Sopenharmony_ci	"AT WS\r",        /* v1.0: Warm Start */
21462306a36Sopenharmony_ci	"AT PP FF OFF\r", /* v1.0: All Programmable Parameters Off */
21562306a36Sopenharmony_ci	"AT M0\r",        /* v1.0: Memory Off */
21662306a36Sopenharmony_ci	"AT AL\r",        /* v1.0: Allow Long messages */
21762306a36Sopenharmony_ci	"AT BI\r",        /* v1.0: Bypass Initialisation */
21862306a36Sopenharmony_ci	"AT CAF0\r",      /* v1.0: CAN Auto Formatting Off */
21962306a36Sopenharmony_ci	"AT CFC0\r",      /* v1.0: CAN Flow Control Off */
22062306a36Sopenharmony_ci	"AT CF 000\r",    /* v1.0: Reset CAN ID Filter */
22162306a36Sopenharmony_ci	"AT CM 000\r",    /* v1.0: Reset CAN ID Mask */
22262306a36Sopenharmony_ci	"AT E1\r",        /* v1.0: Echo On */
22362306a36Sopenharmony_ci	"AT H1\r",        /* v1.0: Headers On */
22462306a36Sopenharmony_ci	"AT L0\r",        /* v1.0: Linefeeds Off */
22562306a36Sopenharmony_ci	"AT SH 7DF\r",    /* v1.0: Set CAN sending ID to 0x7df */
22662306a36Sopenharmony_ci	"AT ST FF\r",     /* v1.0: Set maximum Timeout for response after TX */
22762306a36Sopenharmony_ci	"AT AT0\r",       /* v1.2: Adaptive Timing Off */
22862306a36Sopenharmony_ci	"AT D1\r",        /* v1.3: Print DLC On */
22962306a36Sopenharmony_ci	"AT S1\r",        /* v1.3: Spaces On */
23062306a36Sopenharmony_ci	"AT TP B\r",      /* v1.0: Try Protocol B */
23162306a36Sopenharmony_ci	NULL
23262306a36Sopenharmony_ci};
23362306a36Sopenharmony_ci
23462306a36Sopenharmony_cistatic void can327_init_device(struct can327 *elm)
23562306a36Sopenharmony_ci{
23662306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
23762306a36Sopenharmony_ci
23862306a36Sopenharmony_ci	elm->state = CAN327_STATE_NOTINIT;
23962306a36Sopenharmony_ci	elm->can_frame_to_send.can_id = 0x7df; /* ELM327 HW default */
24062306a36Sopenharmony_ci	elm->rxfill = 0;
24162306a36Sopenharmony_ci	elm->drop_next_line = 0;
24262306a36Sopenharmony_ci
24362306a36Sopenharmony_ci	/* We can only set the bitrate as a fraction of 500000.
24462306a36Sopenharmony_ci	 * The bitrates listed in can327_bitrate_const will
24562306a36Sopenharmony_ci	 * limit the user to the right values.
24662306a36Sopenharmony_ci	 */
24762306a36Sopenharmony_ci	elm->can_bitrate_divisor = 500000 / elm->can.bittiming.bitrate;
24862306a36Sopenharmony_ci	elm->can_config =
24962306a36Sopenharmony_ci		CAN327_CAN_CONFIG_SEND_SFF | CAN327_CAN_CONFIG_VARIABLE_DLC |
25062306a36Sopenharmony_ci		CAN327_CAN_CONFIG_RECV_BOTH_SFF_EFF | elm->can_bitrate_divisor;
25162306a36Sopenharmony_ci
25262306a36Sopenharmony_ci	/* Configure ELM327 and then start monitoring */
25362306a36Sopenharmony_ci	elm->next_init_cmd = &can327_init_script[0];
25462306a36Sopenharmony_ci	set_bit(CAN327_TX_DO_INIT, &elm->cmds_todo);
25562306a36Sopenharmony_ci	set_bit(CAN327_TX_DO_SILENT_MONITOR, &elm->cmds_todo);
25662306a36Sopenharmony_ci	set_bit(CAN327_TX_DO_RESPONSES, &elm->cmds_todo);
25762306a36Sopenharmony_ci	set_bit(CAN327_TX_DO_CAN_CONFIG, &elm->cmds_todo);
25862306a36Sopenharmony_ci
25962306a36Sopenharmony_ci	can327_kick_into_cmd_mode(elm);
26062306a36Sopenharmony_ci}
26162306a36Sopenharmony_ci
26262306a36Sopenharmony_cistatic void can327_feed_frame_to_netdev(struct can327 *elm, struct sk_buff *skb)
26362306a36Sopenharmony_ci{
26462306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
26562306a36Sopenharmony_ci
26662306a36Sopenharmony_ci	if (!netif_running(elm->dev)) {
26762306a36Sopenharmony_ci		kfree_skb(skb);
26862306a36Sopenharmony_ci		return;
26962306a36Sopenharmony_ci	}
27062306a36Sopenharmony_ci
27162306a36Sopenharmony_ci	/* Queue for NAPI pickup.
27262306a36Sopenharmony_ci	 * rx-offload will update stats and LEDs for us.
27362306a36Sopenharmony_ci	 */
27462306a36Sopenharmony_ci	if (can_rx_offload_queue_tail(&elm->offload, skb))
27562306a36Sopenharmony_ci		elm->dev->stats.rx_fifo_errors++;
27662306a36Sopenharmony_ci
27762306a36Sopenharmony_ci	/* Wake NAPI */
27862306a36Sopenharmony_ci	can_rx_offload_irq_finish(&elm->offload);
27962306a36Sopenharmony_ci}
28062306a36Sopenharmony_ci
28162306a36Sopenharmony_ci/* Called when we're out of ideas and just want it all to end. */
28262306a36Sopenharmony_cistatic inline void can327_uart_side_failure(struct can327 *elm)
28362306a36Sopenharmony_ci{
28462306a36Sopenharmony_ci	struct can_frame *frame;
28562306a36Sopenharmony_ci	struct sk_buff *skb;
28662306a36Sopenharmony_ci
28762306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
28862306a36Sopenharmony_ci
28962306a36Sopenharmony_ci	elm->uart_side_failure = true;
29062306a36Sopenharmony_ci
29162306a36Sopenharmony_ci	clear_bit(TTY_DO_WRITE_WAKEUP, &elm->tty->flags);
29262306a36Sopenharmony_ci
29362306a36Sopenharmony_ci	elm->can.can_stats.bus_off++;
29462306a36Sopenharmony_ci	netif_stop_queue(elm->dev);
29562306a36Sopenharmony_ci	elm->can.state = CAN_STATE_BUS_OFF;
29662306a36Sopenharmony_ci	can_bus_off(elm->dev);
29762306a36Sopenharmony_ci
29862306a36Sopenharmony_ci	netdev_err(elm->dev,
29962306a36Sopenharmony_ci		   "ELM327 misbehaved. Blocking further communication.\n");
30062306a36Sopenharmony_ci
30162306a36Sopenharmony_ci	skb = alloc_can_err_skb(elm->dev, &frame);
30262306a36Sopenharmony_ci	if (!skb)
30362306a36Sopenharmony_ci		return;
30462306a36Sopenharmony_ci
30562306a36Sopenharmony_ci	frame->can_id |= CAN_ERR_BUSOFF;
30662306a36Sopenharmony_ci	can327_feed_frame_to_netdev(elm, skb);
30762306a36Sopenharmony_ci}
30862306a36Sopenharmony_ci
30962306a36Sopenharmony_ci/* Compares a byte buffer (non-NUL terminated) to the payload part of
31062306a36Sopenharmony_ci * a string, and returns true iff the buffer (content *and* length) is
31162306a36Sopenharmony_ci * exactly that string, without the terminating NUL byte.
31262306a36Sopenharmony_ci *
31362306a36Sopenharmony_ci * Example: If reference is "BUS ERROR", then this returns true iff nbytes == 9
31462306a36Sopenharmony_ci *          and !memcmp(buf, "BUS ERROR", 9).
31562306a36Sopenharmony_ci *
31662306a36Sopenharmony_ci * The reason to use strings is so we can easily include them in the C
31762306a36Sopenharmony_ci * code, and to avoid hardcoding lengths.
31862306a36Sopenharmony_ci */
31962306a36Sopenharmony_cistatic inline bool can327_rxbuf_cmp(const u8 *buf, size_t nbytes,
32062306a36Sopenharmony_ci				    const char *reference)
32162306a36Sopenharmony_ci{
32262306a36Sopenharmony_ci	size_t ref_len = strlen(reference);
32362306a36Sopenharmony_ci
32462306a36Sopenharmony_ci	return (nbytes == ref_len) && !memcmp(buf, reference, ref_len);
32562306a36Sopenharmony_ci}
32662306a36Sopenharmony_ci
32762306a36Sopenharmony_cistatic void can327_parse_error(struct can327 *elm, size_t len)
32862306a36Sopenharmony_ci{
32962306a36Sopenharmony_ci	struct can_frame *frame;
33062306a36Sopenharmony_ci	struct sk_buff *skb;
33162306a36Sopenharmony_ci
33262306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
33362306a36Sopenharmony_ci
33462306a36Sopenharmony_ci	skb = alloc_can_err_skb(elm->dev, &frame);
33562306a36Sopenharmony_ci	if (!skb)
33662306a36Sopenharmony_ci		/* It's okay to return here:
33762306a36Sopenharmony_ci		 * The outer parsing loop will drop this UART buffer.
33862306a36Sopenharmony_ci		 */
33962306a36Sopenharmony_ci		return;
34062306a36Sopenharmony_ci
34162306a36Sopenharmony_ci	/* Filter possible error messages based on length of RX'd line */
34262306a36Sopenharmony_ci	if (can327_rxbuf_cmp(elm->rxbuf, len, "UNABLE TO CONNECT")) {
34362306a36Sopenharmony_ci		netdev_err(elm->dev,
34462306a36Sopenharmony_ci			   "ELM327 reported UNABLE TO CONNECT. Please check your setup.\n");
34562306a36Sopenharmony_ci	} else if (can327_rxbuf_cmp(elm->rxbuf, len, "BUFFER FULL")) {
34662306a36Sopenharmony_ci		/* This will only happen if the last data line was complete.
34762306a36Sopenharmony_ci		 * Otherwise, can327_parse_frame() will heuristically
34862306a36Sopenharmony_ci		 * emit this kind of error frame instead.
34962306a36Sopenharmony_ci		 */
35062306a36Sopenharmony_ci		frame->can_id |= CAN_ERR_CRTL;
35162306a36Sopenharmony_ci		frame->data[1] = CAN_ERR_CRTL_RX_OVERFLOW;
35262306a36Sopenharmony_ci	} else if (can327_rxbuf_cmp(elm->rxbuf, len, "BUS ERROR")) {
35362306a36Sopenharmony_ci		frame->can_id |= CAN_ERR_BUSERROR;
35462306a36Sopenharmony_ci	} else if (can327_rxbuf_cmp(elm->rxbuf, len, "CAN ERROR")) {
35562306a36Sopenharmony_ci		frame->can_id |= CAN_ERR_PROT;
35662306a36Sopenharmony_ci	} else if (can327_rxbuf_cmp(elm->rxbuf, len, "<RX ERROR")) {
35762306a36Sopenharmony_ci		frame->can_id |= CAN_ERR_PROT;
35862306a36Sopenharmony_ci	} else if (can327_rxbuf_cmp(elm->rxbuf, len, "BUS BUSY")) {
35962306a36Sopenharmony_ci		frame->can_id |= CAN_ERR_PROT;
36062306a36Sopenharmony_ci		frame->data[2] = CAN_ERR_PROT_OVERLOAD;
36162306a36Sopenharmony_ci	} else if (can327_rxbuf_cmp(elm->rxbuf, len, "FB ERROR")) {
36262306a36Sopenharmony_ci		frame->can_id |= CAN_ERR_PROT;
36362306a36Sopenharmony_ci		frame->data[2] = CAN_ERR_PROT_TX;
36462306a36Sopenharmony_ci	} else if (len == 5 && !memcmp(elm->rxbuf, "ERR", 3)) {
36562306a36Sopenharmony_ci		/* ERR is followed by two digits, hence line length 5 */
36662306a36Sopenharmony_ci		netdev_err(elm->dev, "ELM327 reported an ERR%c%c. Please power it off and on again.\n",
36762306a36Sopenharmony_ci			   elm->rxbuf[3], elm->rxbuf[4]);
36862306a36Sopenharmony_ci		frame->can_id |= CAN_ERR_CRTL;
36962306a36Sopenharmony_ci	} else {
37062306a36Sopenharmony_ci		/* Something else has happened.
37162306a36Sopenharmony_ci		 * Maybe garbage on the UART line.
37262306a36Sopenharmony_ci		 * Emit a generic error frame.
37362306a36Sopenharmony_ci		 */
37462306a36Sopenharmony_ci	}
37562306a36Sopenharmony_ci
37662306a36Sopenharmony_ci	can327_feed_frame_to_netdev(elm, skb);
37762306a36Sopenharmony_ci}
37862306a36Sopenharmony_ci
37962306a36Sopenharmony_ci/* Parse CAN frames coming as ASCII from ELM327.
38062306a36Sopenharmony_ci * They can be of various formats:
38162306a36Sopenharmony_ci *
38262306a36Sopenharmony_ci * 29-bit ID (EFF):  12 34 56 78 D PL PL PL PL PL PL PL PL
38362306a36Sopenharmony_ci * 11-bit ID (!EFF): 123 D PL PL PL PL PL PL PL PL
38462306a36Sopenharmony_ci *
38562306a36Sopenharmony_ci * where D = DLC, PL = payload byte
38662306a36Sopenharmony_ci *
38762306a36Sopenharmony_ci * Instead of a payload, RTR indicates a remote request.
38862306a36Sopenharmony_ci *
38962306a36Sopenharmony_ci * We will use the spaces and line length to guess the format.
39062306a36Sopenharmony_ci */
39162306a36Sopenharmony_cistatic int can327_parse_frame(struct can327 *elm, size_t len)
39262306a36Sopenharmony_ci{
39362306a36Sopenharmony_ci	struct can_frame *frame;
39462306a36Sopenharmony_ci	struct sk_buff *skb;
39562306a36Sopenharmony_ci	int hexlen;
39662306a36Sopenharmony_ci	int datastart;
39762306a36Sopenharmony_ci	int i;
39862306a36Sopenharmony_ci
39962306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
40062306a36Sopenharmony_ci
40162306a36Sopenharmony_ci	skb = alloc_can_skb(elm->dev, &frame);
40262306a36Sopenharmony_ci	if (!skb)
40362306a36Sopenharmony_ci		return -ENOMEM;
40462306a36Sopenharmony_ci
40562306a36Sopenharmony_ci	/* Find first non-hex and non-space character:
40662306a36Sopenharmony_ci	 *  - In the simplest case, there is none.
40762306a36Sopenharmony_ci	 *  - For RTR frames, 'R' is the first non-hex character.
40862306a36Sopenharmony_ci	 *  - An error message may replace the end of the data line.
40962306a36Sopenharmony_ci	 */
41062306a36Sopenharmony_ci	for (hexlen = 0; hexlen <= len; hexlen++) {
41162306a36Sopenharmony_ci		if (hex_to_bin(elm->rxbuf[hexlen]) < 0 &&
41262306a36Sopenharmony_ci		    elm->rxbuf[hexlen] != ' ') {
41362306a36Sopenharmony_ci			break;
41462306a36Sopenharmony_ci		}
41562306a36Sopenharmony_ci	}
41662306a36Sopenharmony_ci
41762306a36Sopenharmony_ci	/* Sanity check whether the line is really a clean hexdump,
41862306a36Sopenharmony_ci	 * or terminated by an error message, or contains garbage.
41962306a36Sopenharmony_ci	 */
42062306a36Sopenharmony_ci	if (hexlen < len && !isdigit(elm->rxbuf[hexlen]) &&
42162306a36Sopenharmony_ci	    !isupper(elm->rxbuf[hexlen]) && '<' != elm->rxbuf[hexlen] &&
42262306a36Sopenharmony_ci	    ' ' != elm->rxbuf[hexlen]) {
42362306a36Sopenharmony_ci		/* The line is likely garbled anyway, so bail.
42462306a36Sopenharmony_ci		 * The main code will restart listening.
42562306a36Sopenharmony_ci		 */
42662306a36Sopenharmony_ci		kfree_skb(skb);
42762306a36Sopenharmony_ci		return -ENODATA;
42862306a36Sopenharmony_ci	}
42962306a36Sopenharmony_ci
43062306a36Sopenharmony_ci	/* Use spaces in CAN ID to distinguish 29 or 11 bit address length.
43162306a36Sopenharmony_ci	 * No out-of-bounds access:
43262306a36Sopenharmony_ci	 * We use the fact that we can always read from elm->rxbuf.
43362306a36Sopenharmony_ci	 */
43462306a36Sopenharmony_ci	if (elm->rxbuf[2] == ' ' && elm->rxbuf[5] == ' ' &&
43562306a36Sopenharmony_ci	    elm->rxbuf[8] == ' ' && elm->rxbuf[11] == ' ' &&
43662306a36Sopenharmony_ci	    elm->rxbuf[13] == ' ') {
43762306a36Sopenharmony_ci		frame->can_id = CAN_EFF_FLAG;
43862306a36Sopenharmony_ci		datastart = 14;
43962306a36Sopenharmony_ci	} else if (elm->rxbuf[3] == ' ' && elm->rxbuf[5] == ' ') {
44062306a36Sopenharmony_ci		datastart = 6;
44162306a36Sopenharmony_ci	} else {
44262306a36Sopenharmony_ci		/* This is not a well-formatted data line.
44362306a36Sopenharmony_ci		 * Assume it's an error message.
44462306a36Sopenharmony_ci		 */
44562306a36Sopenharmony_ci		kfree_skb(skb);
44662306a36Sopenharmony_ci		return -ENODATA;
44762306a36Sopenharmony_ci	}
44862306a36Sopenharmony_ci
44962306a36Sopenharmony_ci	if (hexlen < datastart) {
45062306a36Sopenharmony_ci		/* The line is too short to be a valid frame hex dump.
45162306a36Sopenharmony_ci		 * Something interrupted the hex dump or it is invalid.
45262306a36Sopenharmony_ci		 */
45362306a36Sopenharmony_ci		kfree_skb(skb);
45462306a36Sopenharmony_ci		return -ENODATA;
45562306a36Sopenharmony_ci	}
45662306a36Sopenharmony_ci
45762306a36Sopenharmony_ci	/* From here on all chars up to buf[hexlen] are hex or spaces,
45862306a36Sopenharmony_ci	 * at well-defined offsets.
45962306a36Sopenharmony_ci	 */
46062306a36Sopenharmony_ci
46162306a36Sopenharmony_ci	/* Read CAN data length */
46262306a36Sopenharmony_ci	frame->len = (hex_to_bin(elm->rxbuf[datastart - 2]) << 0);
46362306a36Sopenharmony_ci
46462306a36Sopenharmony_ci	/* Read CAN ID */
46562306a36Sopenharmony_ci	if (frame->can_id & CAN_EFF_FLAG) {
46662306a36Sopenharmony_ci		frame->can_id |= (hex_to_bin(elm->rxbuf[0]) << 28) |
46762306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[1]) << 24) |
46862306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[3]) << 20) |
46962306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[4]) << 16) |
47062306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[6]) << 12) |
47162306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[7]) << 8) |
47262306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[9]) << 4) |
47362306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[10]) << 0);
47462306a36Sopenharmony_ci	} else {
47562306a36Sopenharmony_ci		frame->can_id |= (hex_to_bin(elm->rxbuf[0]) << 8) |
47662306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[1]) << 4) |
47762306a36Sopenharmony_ci				 (hex_to_bin(elm->rxbuf[2]) << 0);
47862306a36Sopenharmony_ci	}
47962306a36Sopenharmony_ci
48062306a36Sopenharmony_ci	/* Check for RTR frame */
48162306a36Sopenharmony_ci	if (elm->rxfill >= hexlen + 3 &&
48262306a36Sopenharmony_ci	    !memcmp(&elm->rxbuf[hexlen], "RTR", 3)) {
48362306a36Sopenharmony_ci		frame->can_id |= CAN_RTR_FLAG;
48462306a36Sopenharmony_ci	}
48562306a36Sopenharmony_ci
48662306a36Sopenharmony_ci	/* Is the line long enough to hold the advertised payload?
48762306a36Sopenharmony_ci	 * Note: RTR frames have a DLC, but no actual payload.
48862306a36Sopenharmony_ci	 */
48962306a36Sopenharmony_ci	if (!(frame->can_id & CAN_RTR_FLAG) &&
49062306a36Sopenharmony_ci	    (hexlen < frame->len * 3 + datastart)) {
49162306a36Sopenharmony_ci		/* Incomplete frame.
49262306a36Sopenharmony_ci		 * Probably the ELM327's RS232 TX buffer was full.
49362306a36Sopenharmony_ci		 * Emit an error frame and exit.
49462306a36Sopenharmony_ci		 */
49562306a36Sopenharmony_ci		frame->can_id = CAN_ERR_FLAG | CAN_ERR_CRTL;
49662306a36Sopenharmony_ci		frame->len = CAN_ERR_DLC;
49762306a36Sopenharmony_ci		frame->data[1] = CAN_ERR_CRTL_RX_OVERFLOW;
49862306a36Sopenharmony_ci		can327_feed_frame_to_netdev(elm, skb);
49962306a36Sopenharmony_ci
50062306a36Sopenharmony_ci		/* Signal failure to parse.
50162306a36Sopenharmony_ci		 * The line will be re-parsed as an error line, which will fail.
50262306a36Sopenharmony_ci		 * However, this will correctly drop the state machine back into
50362306a36Sopenharmony_ci		 * command mode.
50462306a36Sopenharmony_ci		 */
50562306a36Sopenharmony_ci		return -ENODATA;
50662306a36Sopenharmony_ci	}
50762306a36Sopenharmony_ci
50862306a36Sopenharmony_ci	/* Parse the data nibbles. */
50962306a36Sopenharmony_ci	for (i = 0; i < frame->len; i++) {
51062306a36Sopenharmony_ci		frame->data[i] =
51162306a36Sopenharmony_ci			(hex_to_bin(elm->rxbuf[datastart + 3 * i]) << 4) |
51262306a36Sopenharmony_ci			(hex_to_bin(elm->rxbuf[datastart + 3 * i + 1]));
51362306a36Sopenharmony_ci	}
51462306a36Sopenharmony_ci
51562306a36Sopenharmony_ci	/* Feed the frame to the network layer. */
51662306a36Sopenharmony_ci	can327_feed_frame_to_netdev(elm, skb);
51762306a36Sopenharmony_ci
51862306a36Sopenharmony_ci	return 0;
51962306a36Sopenharmony_ci}
52062306a36Sopenharmony_ci
52162306a36Sopenharmony_cistatic void can327_parse_line(struct can327 *elm, size_t len)
52262306a36Sopenharmony_ci{
52362306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
52462306a36Sopenharmony_ci
52562306a36Sopenharmony_ci	/* Skip empty lines */
52662306a36Sopenharmony_ci	if (!len)
52762306a36Sopenharmony_ci		return;
52862306a36Sopenharmony_ci
52962306a36Sopenharmony_ci	/* Skip echo lines */
53062306a36Sopenharmony_ci	if (elm->drop_next_line) {
53162306a36Sopenharmony_ci		elm->drop_next_line = 0;
53262306a36Sopenharmony_ci		return;
53362306a36Sopenharmony_ci	} else if (!memcmp(elm->rxbuf, "AT", 2)) {
53462306a36Sopenharmony_ci		return;
53562306a36Sopenharmony_ci	}
53662306a36Sopenharmony_ci
53762306a36Sopenharmony_ci	/* Regular parsing */
53862306a36Sopenharmony_ci	if (elm->state == CAN327_STATE_RECEIVING &&
53962306a36Sopenharmony_ci	    can327_parse_frame(elm, len)) {
54062306a36Sopenharmony_ci		/* Parse an error line. */
54162306a36Sopenharmony_ci		can327_parse_error(elm, len);
54262306a36Sopenharmony_ci
54362306a36Sopenharmony_ci		/* Start afresh. */
54462306a36Sopenharmony_ci		can327_kick_into_cmd_mode(elm);
54562306a36Sopenharmony_ci	}
54662306a36Sopenharmony_ci}
54762306a36Sopenharmony_ci
54862306a36Sopenharmony_cistatic void can327_handle_prompt(struct can327 *elm)
54962306a36Sopenharmony_ci{
55062306a36Sopenharmony_ci	struct can_frame *frame = &elm->can_frame_to_send;
55162306a36Sopenharmony_ci	/* Size this buffer for the largest ELM327 line we may generate,
55262306a36Sopenharmony_ci	 * which is currently an 8 byte CAN frame's payload hexdump.
55362306a36Sopenharmony_ci	 * Items in can327_init_script must fit here, too!
55462306a36Sopenharmony_ci	 */
55562306a36Sopenharmony_ci	char local_txbuf[sizeof("0102030405060708\r")];
55662306a36Sopenharmony_ci
55762306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
55862306a36Sopenharmony_ci
55962306a36Sopenharmony_ci	if (!elm->cmds_todo) {
56062306a36Sopenharmony_ci		/* Enter CAN monitor mode */
56162306a36Sopenharmony_ci		can327_send(elm, "ATMA\r", 5);
56262306a36Sopenharmony_ci		elm->state = CAN327_STATE_RECEIVING;
56362306a36Sopenharmony_ci
56462306a36Sopenharmony_ci		/* We will be in the default state once this command is
56562306a36Sopenharmony_ci		 * sent, so enable the TX packet queue.
56662306a36Sopenharmony_ci		 */
56762306a36Sopenharmony_ci		netif_wake_queue(elm->dev);
56862306a36Sopenharmony_ci
56962306a36Sopenharmony_ci		return;
57062306a36Sopenharmony_ci	}
57162306a36Sopenharmony_ci
57262306a36Sopenharmony_ci	/* Reconfigure ELM327 step by step as indicated by elm->cmds_todo */
57362306a36Sopenharmony_ci	if (test_bit(CAN327_TX_DO_INIT, &elm->cmds_todo)) {
57462306a36Sopenharmony_ci		snprintf(local_txbuf, sizeof(local_txbuf), "%s",
57562306a36Sopenharmony_ci			 *elm->next_init_cmd);
57662306a36Sopenharmony_ci
57762306a36Sopenharmony_ci		elm->next_init_cmd++;
57862306a36Sopenharmony_ci		if (!(*elm->next_init_cmd)) {
57962306a36Sopenharmony_ci			clear_bit(CAN327_TX_DO_INIT, &elm->cmds_todo);
58062306a36Sopenharmony_ci			/* Init finished. */
58162306a36Sopenharmony_ci		}
58262306a36Sopenharmony_ci
58362306a36Sopenharmony_ci	} else if (test_and_clear_bit(CAN327_TX_DO_SILENT_MONITOR, &elm->cmds_todo)) {
58462306a36Sopenharmony_ci		snprintf(local_txbuf, sizeof(local_txbuf),
58562306a36Sopenharmony_ci			 "ATCSM%i\r",
58662306a36Sopenharmony_ci			 !!(elm->can.ctrlmode & CAN_CTRLMODE_LISTENONLY));
58762306a36Sopenharmony_ci
58862306a36Sopenharmony_ci	} else if (test_and_clear_bit(CAN327_TX_DO_RESPONSES, &elm->cmds_todo)) {
58962306a36Sopenharmony_ci		snprintf(local_txbuf, sizeof(local_txbuf),
59062306a36Sopenharmony_ci			 "ATR%i\r",
59162306a36Sopenharmony_ci			 !(elm->can.ctrlmode & CAN_CTRLMODE_LISTENONLY));
59262306a36Sopenharmony_ci
59362306a36Sopenharmony_ci	} else if (test_and_clear_bit(CAN327_TX_DO_CAN_CONFIG, &elm->cmds_todo)) {
59462306a36Sopenharmony_ci		snprintf(local_txbuf, sizeof(local_txbuf),
59562306a36Sopenharmony_ci			 "ATPC\r");
59662306a36Sopenharmony_ci		set_bit(CAN327_TX_DO_CAN_CONFIG_PART2, &elm->cmds_todo);
59762306a36Sopenharmony_ci
59862306a36Sopenharmony_ci	} else if (test_and_clear_bit(CAN327_TX_DO_CAN_CONFIG_PART2, &elm->cmds_todo)) {
59962306a36Sopenharmony_ci		snprintf(local_txbuf, sizeof(local_txbuf),
60062306a36Sopenharmony_ci			 "ATPB%04X\r",
60162306a36Sopenharmony_ci			 elm->can_config);
60262306a36Sopenharmony_ci
60362306a36Sopenharmony_ci	} else if (test_and_clear_bit(CAN327_TX_DO_CANID_29BIT_HIGH, &elm->cmds_todo)) {
60462306a36Sopenharmony_ci		snprintf(local_txbuf, sizeof(local_txbuf),
60562306a36Sopenharmony_ci			 "ATCP%02X\r",
60662306a36Sopenharmony_ci			 (frame->can_id & CAN_EFF_MASK) >> 24);
60762306a36Sopenharmony_ci
60862306a36Sopenharmony_ci	} else if (test_and_clear_bit(CAN327_TX_DO_CANID_29BIT_LOW, &elm->cmds_todo)) {
60962306a36Sopenharmony_ci		snprintf(local_txbuf, sizeof(local_txbuf),
61062306a36Sopenharmony_ci			 "ATSH%06X\r",
61162306a36Sopenharmony_ci			 frame->can_id & CAN_EFF_MASK & ((1 << 24) - 1));
61262306a36Sopenharmony_ci
61362306a36Sopenharmony_ci	} else if (test_and_clear_bit(CAN327_TX_DO_CANID_11BIT, &elm->cmds_todo)) {
61462306a36Sopenharmony_ci		snprintf(local_txbuf, sizeof(local_txbuf),
61562306a36Sopenharmony_ci			 "ATSH%03X\r",
61662306a36Sopenharmony_ci			 frame->can_id & CAN_SFF_MASK);
61762306a36Sopenharmony_ci
61862306a36Sopenharmony_ci	} else if (test_and_clear_bit(CAN327_TX_DO_CAN_DATA, &elm->cmds_todo)) {
61962306a36Sopenharmony_ci		if (frame->can_id & CAN_RTR_FLAG) {
62062306a36Sopenharmony_ci			/* Send an RTR frame. Their DLC is fixed.
62162306a36Sopenharmony_ci			 * Some chips don't send them at all.
62262306a36Sopenharmony_ci			 */
62362306a36Sopenharmony_ci			snprintf(local_txbuf, sizeof(local_txbuf), "ATRTR\r");
62462306a36Sopenharmony_ci		} else {
62562306a36Sopenharmony_ci			/* Send a regular CAN data frame */
62662306a36Sopenharmony_ci			int i;
62762306a36Sopenharmony_ci
62862306a36Sopenharmony_ci			for (i = 0; i < frame->len; i++) {
62962306a36Sopenharmony_ci				snprintf(&local_txbuf[2 * i],
63062306a36Sopenharmony_ci					 sizeof(local_txbuf), "%02X",
63162306a36Sopenharmony_ci					 frame->data[i]);
63262306a36Sopenharmony_ci			}
63362306a36Sopenharmony_ci
63462306a36Sopenharmony_ci			snprintf(&local_txbuf[2 * i], sizeof(local_txbuf),
63562306a36Sopenharmony_ci				 "\r");
63662306a36Sopenharmony_ci		}
63762306a36Sopenharmony_ci
63862306a36Sopenharmony_ci		elm->drop_next_line = 1;
63962306a36Sopenharmony_ci		elm->state = CAN327_STATE_RECEIVING;
64062306a36Sopenharmony_ci
64162306a36Sopenharmony_ci		/* We will be in the default state once this command is
64262306a36Sopenharmony_ci		 * sent, so enable the TX packet queue.
64362306a36Sopenharmony_ci		 */
64462306a36Sopenharmony_ci		netif_wake_queue(elm->dev);
64562306a36Sopenharmony_ci	}
64662306a36Sopenharmony_ci
64762306a36Sopenharmony_ci	can327_send(elm, local_txbuf, strlen(local_txbuf));
64862306a36Sopenharmony_ci}
64962306a36Sopenharmony_ci
65062306a36Sopenharmony_cistatic bool can327_is_ready_char(char c)
65162306a36Sopenharmony_ci{
65262306a36Sopenharmony_ci	/* Bits 0xc0 are sometimes set (randomly), hence the mask.
65362306a36Sopenharmony_ci	 * Probably bad hardware.
65462306a36Sopenharmony_ci	 */
65562306a36Sopenharmony_ci	return (c & 0x3f) == CAN327_READY_CHAR;
65662306a36Sopenharmony_ci}
65762306a36Sopenharmony_ci
65862306a36Sopenharmony_cistatic void can327_drop_bytes(struct can327 *elm, size_t i)
65962306a36Sopenharmony_ci{
66062306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
66162306a36Sopenharmony_ci
66262306a36Sopenharmony_ci	memmove(&elm->rxbuf[0], &elm->rxbuf[i], CAN327_SIZE_RXBUF - i);
66362306a36Sopenharmony_ci	elm->rxfill -= i;
66462306a36Sopenharmony_ci}
66562306a36Sopenharmony_ci
66662306a36Sopenharmony_cistatic void can327_parse_rxbuf(struct can327 *elm, size_t first_new_char_idx)
66762306a36Sopenharmony_ci{
66862306a36Sopenharmony_ci	size_t len, pos;
66962306a36Sopenharmony_ci
67062306a36Sopenharmony_ci	lockdep_assert_held(&elm->lock);
67162306a36Sopenharmony_ci
67262306a36Sopenharmony_ci	switch (elm->state) {
67362306a36Sopenharmony_ci	case CAN327_STATE_NOTINIT:
67462306a36Sopenharmony_ci		elm->rxfill = 0;
67562306a36Sopenharmony_ci		break;
67662306a36Sopenharmony_ci
67762306a36Sopenharmony_ci	case CAN327_STATE_GETDUMMYCHAR:
67862306a36Sopenharmony_ci		/* Wait for 'y' or '>' */
67962306a36Sopenharmony_ci		for (pos = 0; pos < elm->rxfill; pos++) {
68062306a36Sopenharmony_ci			if (elm->rxbuf[pos] == CAN327_DUMMY_CHAR) {
68162306a36Sopenharmony_ci				can327_send(elm, "\r", 1);
68262306a36Sopenharmony_ci				elm->state = CAN327_STATE_GETPROMPT;
68362306a36Sopenharmony_ci				pos++;
68462306a36Sopenharmony_ci				break;
68562306a36Sopenharmony_ci			} else if (can327_is_ready_char(elm->rxbuf[pos])) {
68662306a36Sopenharmony_ci				can327_send(elm, CAN327_DUMMY_STRING, 1);
68762306a36Sopenharmony_ci				pos++;
68862306a36Sopenharmony_ci				break;
68962306a36Sopenharmony_ci			}
69062306a36Sopenharmony_ci		}
69162306a36Sopenharmony_ci
69262306a36Sopenharmony_ci		can327_drop_bytes(elm, pos);
69362306a36Sopenharmony_ci		break;
69462306a36Sopenharmony_ci
69562306a36Sopenharmony_ci	case CAN327_STATE_GETPROMPT:
69662306a36Sopenharmony_ci		/* Wait for '>' */
69762306a36Sopenharmony_ci		if (can327_is_ready_char(elm->rxbuf[elm->rxfill - 1]))
69862306a36Sopenharmony_ci			can327_handle_prompt(elm);
69962306a36Sopenharmony_ci
70062306a36Sopenharmony_ci		elm->rxfill = 0;
70162306a36Sopenharmony_ci		break;
70262306a36Sopenharmony_ci
70362306a36Sopenharmony_ci	case CAN327_STATE_RECEIVING:
70462306a36Sopenharmony_ci		/* Find <CR> delimiting feedback lines. */
70562306a36Sopenharmony_ci		len = first_new_char_idx;
70662306a36Sopenharmony_ci		while (len < elm->rxfill && elm->rxbuf[len] != '\r')
70762306a36Sopenharmony_ci			len++;
70862306a36Sopenharmony_ci
70962306a36Sopenharmony_ci		if (len == CAN327_SIZE_RXBUF) {
71062306a36Sopenharmony_ci			/* Assume the buffer ran full with garbage.
71162306a36Sopenharmony_ci			 * Did we even connect at the right baud rate?
71262306a36Sopenharmony_ci			 */
71362306a36Sopenharmony_ci			netdev_err(elm->dev,
71462306a36Sopenharmony_ci				   "RX buffer overflow. Faulty ELM327 or UART?\n");
71562306a36Sopenharmony_ci			can327_uart_side_failure(elm);
71662306a36Sopenharmony_ci		} else if (len == elm->rxfill) {
71762306a36Sopenharmony_ci			if (can327_is_ready_char(elm->rxbuf[elm->rxfill - 1])) {
71862306a36Sopenharmony_ci				/* The ELM327's AT ST response timeout ran out,
71962306a36Sopenharmony_ci				 * so we got a prompt.
72062306a36Sopenharmony_ci				 * Clear RX buffer and restart listening.
72162306a36Sopenharmony_ci				 */
72262306a36Sopenharmony_ci				elm->rxfill = 0;
72362306a36Sopenharmony_ci
72462306a36Sopenharmony_ci				can327_handle_prompt(elm);
72562306a36Sopenharmony_ci			}
72662306a36Sopenharmony_ci
72762306a36Sopenharmony_ci			/* No <CR> found - we haven't received a full line yet.
72862306a36Sopenharmony_ci			 * Wait for more data.
72962306a36Sopenharmony_ci			 */
73062306a36Sopenharmony_ci		} else {
73162306a36Sopenharmony_ci			/* We have a full line to parse. */
73262306a36Sopenharmony_ci			can327_parse_line(elm, len);
73362306a36Sopenharmony_ci
73462306a36Sopenharmony_ci			/* Remove parsed data from RX buffer. */
73562306a36Sopenharmony_ci			can327_drop_bytes(elm, len + 1);
73662306a36Sopenharmony_ci
73762306a36Sopenharmony_ci			/* More data to parse? */
73862306a36Sopenharmony_ci			if (elm->rxfill)
73962306a36Sopenharmony_ci				can327_parse_rxbuf(elm, 0);
74062306a36Sopenharmony_ci		}
74162306a36Sopenharmony_ci	}
74262306a36Sopenharmony_ci}
74362306a36Sopenharmony_ci
74462306a36Sopenharmony_cistatic int can327_netdev_open(struct net_device *dev)
74562306a36Sopenharmony_ci{
74662306a36Sopenharmony_ci	struct can327 *elm = netdev_priv(dev);
74762306a36Sopenharmony_ci	int err;
74862306a36Sopenharmony_ci
74962306a36Sopenharmony_ci	spin_lock_bh(&elm->lock);
75062306a36Sopenharmony_ci
75162306a36Sopenharmony_ci	if (!elm->tty) {
75262306a36Sopenharmony_ci		spin_unlock_bh(&elm->lock);
75362306a36Sopenharmony_ci		return -ENODEV;
75462306a36Sopenharmony_ci	}
75562306a36Sopenharmony_ci
75662306a36Sopenharmony_ci	if (elm->uart_side_failure)
75762306a36Sopenharmony_ci		netdev_warn(elm->dev,
75862306a36Sopenharmony_ci			    "Reopening netdev after a UART side fault has been detected.\n");
75962306a36Sopenharmony_ci
76062306a36Sopenharmony_ci	/* Clear TTY buffers */
76162306a36Sopenharmony_ci	elm->rxfill = 0;
76262306a36Sopenharmony_ci	elm->txleft = 0;
76362306a36Sopenharmony_ci
76462306a36Sopenharmony_ci	/* open_candev() checks for elm->can.bittiming.bitrate != 0 */
76562306a36Sopenharmony_ci	err = open_candev(dev);
76662306a36Sopenharmony_ci	if (err) {
76762306a36Sopenharmony_ci		spin_unlock_bh(&elm->lock);
76862306a36Sopenharmony_ci		return err;
76962306a36Sopenharmony_ci	}
77062306a36Sopenharmony_ci
77162306a36Sopenharmony_ci	can327_init_device(elm);
77262306a36Sopenharmony_ci	spin_unlock_bh(&elm->lock);
77362306a36Sopenharmony_ci
77462306a36Sopenharmony_ci	err = can_rx_offload_add_manual(dev, &elm->offload, CAN327_NAPI_WEIGHT);
77562306a36Sopenharmony_ci	if (err) {
77662306a36Sopenharmony_ci		close_candev(dev);
77762306a36Sopenharmony_ci		return err;
77862306a36Sopenharmony_ci	}
77962306a36Sopenharmony_ci
78062306a36Sopenharmony_ci	can_rx_offload_enable(&elm->offload);
78162306a36Sopenharmony_ci
78262306a36Sopenharmony_ci	elm->can.state = CAN_STATE_ERROR_ACTIVE;
78362306a36Sopenharmony_ci	netif_start_queue(dev);
78462306a36Sopenharmony_ci
78562306a36Sopenharmony_ci	return 0;
78662306a36Sopenharmony_ci}
78762306a36Sopenharmony_ci
78862306a36Sopenharmony_cistatic int can327_netdev_close(struct net_device *dev)
78962306a36Sopenharmony_ci{
79062306a36Sopenharmony_ci	struct can327 *elm = netdev_priv(dev);
79162306a36Sopenharmony_ci
79262306a36Sopenharmony_ci	/* Interrupt whatever the ELM327 is doing right now */
79362306a36Sopenharmony_ci	spin_lock_bh(&elm->lock);
79462306a36Sopenharmony_ci	can327_send(elm, CAN327_DUMMY_STRING, 1);
79562306a36Sopenharmony_ci	spin_unlock_bh(&elm->lock);
79662306a36Sopenharmony_ci
79762306a36Sopenharmony_ci	netif_stop_queue(dev);
79862306a36Sopenharmony_ci
79962306a36Sopenharmony_ci	/* We don't flush the UART TX queue here, as we want final stop
80062306a36Sopenharmony_ci	 * commands (like the above dummy char) to be flushed out.
80162306a36Sopenharmony_ci	 */
80262306a36Sopenharmony_ci
80362306a36Sopenharmony_ci	can_rx_offload_disable(&elm->offload);
80462306a36Sopenharmony_ci	elm->can.state = CAN_STATE_STOPPED;
80562306a36Sopenharmony_ci	can_rx_offload_del(&elm->offload);
80662306a36Sopenharmony_ci	close_candev(dev);
80762306a36Sopenharmony_ci
80862306a36Sopenharmony_ci	return 0;
80962306a36Sopenharmony_ci}
81062306a36Sopenharmony_ci
81162306a36Sopenharmony_ci/* Send a can_frame to a TTY. */
81262306a36Sopenharmony_cistatic netdev_tx_t can327_netdev_start_xmit(struct sk_buff *skb,
81362306a36Sopenharmony_ci					    struct net_device *dev)
81462306a36Sopenharmony_ci{
81562306a36Sopenharmony_ci	struct can327 *elm = netdev_priv(dev);
81662306a36Sopenharmony_ci	struct can_frame *frame = (struct can_frame *)skb->data;
81762306a36Sopenharmony_ci
81862306a36Sopenharmony_ci	if (can_dev_dropped_skb(dev, skb))
81962306a36Sopenharmony_ci		return NETDEV_TX_OK;
82062306a36Sopenharmony_ci
82162306a36Sopenharmony_ci	/* We shouldn't get here after a hardware fault:
82262306a36Sopenharmony_ci	 * can_bus_off() calls netif_carrier_off()
82362306a36Sopenharmony_ci	 */
82462306a36Sopenharmony_ci	if (elm->uart_side_failure) {
82562306a36Sopenharmony_ci		WARN_ON_ONCE(elm->uart_side_failure);
82662306a36Sopenharmony_ci		goto out;
82762306a36Sopenharmony_ci	}
82862306a36Sopenharmony_ci
82962306a36Sopenharmony_ci	netif_stop_queue(dev);
83062306a36Sopenharmony_ci
83162306a36Sopenharmony_ci	/* BHs are already disabled, so no spin_lock_bh().
83262306a36Sopenharmony_ci	 * See Documentation/networking/netdevices.rst
83362306a36Sopenharmony_ci	 */
83462306a36Sopenharmony_ci	spin_lock(&elm->lock);
83562306a36Sopenharmony_ci	can327_send_frame(elm, frame);
83662306a36Sopenharmony_ci	spin_unlock(&elm->lock);
83762306a36Sopenharmony_ci
83862306a36Sopenharmony_ci	dev->stats.tx_packets++;
83962306a36Sopenharmony_ci	dev->stats.tx_bytes += frame->can_id & CAN_RTR_FLAG ? 0 : frame->len;
84062306a36Sopenharmony_ci
84162306a36Sopenharmony_ci	skb_tx_timestamp(skb);
84262306a36Sopenharmony_ci
84362306a36Sopenharmony_ciout:
84462306a36Sopenharmony_ci	kfree_skb(skb);
84562306a36Sopenharmony_ci	return NETDEV_TX_OK;
84662306a36Sopenharmony_ci}
84762306a36Sopenharmony_ci
84862306a36Sopenharmony_cistatic const struct net_device_ops can327_netdev_ops = {
84962306a36Sopenharmony_ci	.ndo_open = can327_netdev_open,
85062306a36Sopenharmony_ci	.ndo_stop = can327_netdev_close,
85162306a36Sopenharmony_ci	.ndo_start_xmit = can327_netdev_start_xmit,
85262306a36Sopenharmony_ci	.ndo_change_mtu = can_change_mtu,
85362306a36Sopenharmony_ci};
85462306a36Sopenharmony_ci
85562306a36Sopenharmony_cistatic const struct ethtool_ops can327_ethtool_ops = {
85662306a36Sopenharmony_ci	.get_ts_info = ethtool_op_get_ts_info,
85762306a36Sopenharmony_ci};
85862306a36Sopenharmony_ci
85962306a36Sopenharmony_cistatic bool can327_is_valid_rx_char(u8 c)
86062306a36Sopenharmony_ci{
86162306a36Sopenharmony_ci	static const bool lut_char_is_valid['z'] = {
86262306a36Sopenharmony_ci		['\r'] = true,
86362306a36Sopenharmony_ci		[' '] = true,
86462306a36Sopenharmony_ci		['.'] = true,
86562306a36Sopenharmony_ci		['0'] = true, true, true, true, true,
86662306a36Sopenharmony_ci		['5'] = true, true, true, true, true,
86762306a36Sopenharmony_ci		['<'] = true,
86862306a36Sopenharmony_ci		[CAN327_READY_CHAR] = true,
86962306a36Sopenharmony_ci		['?'] = true,
87062306a36Sopenharmony_ci		['A'] = true, true, true, true, true, true, true,
87162306a36Sopenharmony_ci		['H'] = true, true, true, true, true, true, true,
87262306a36Sopenharmony_ci		['O'] = true, true, true, true, true, true, true,
87362306a36Sopenharmony_ci		['V'] = true, true, true, true, true,
87462306a36Sopenharmony_ci		['a'] = true,
87562306a36Sopenharmony_ci		['b'] = true,
87662306a36Sopenharmony_ci		['v'] = true,
87762306a36Sopenharmony_ci		[CAN327_DUMMY_CHAR] = true,
87862306a36Sopenharmony_ci	};
87962306a36Sopenharmony_ci	BUILD_BUG_ON(CAN327_DUMMY_CHAR >= 'z');
88062306a36Sopenharmony_ci
88162306a36Sopenharmony_ci	return (c < ARRAY_SIZE(lut_char_is_valid) && lut_char_is_valid[c]);
88262306a36Sopenharmony_ci}
88362306a36Sopenharmony_ci
88462306a36Sopenharmony_ci/* Handle incoming ELM327 ASCII data.
88562306a36Sopenharmony_ci * This will not be re-entered while running, but other ldisc
88662306a36Sopenharmony_ci * functions may be called in parallel.
88762306a36Sopenharmony_ci */
88862306a36Sopenharmony_cistatic void can327_ldisc_rx(struct tty_struct *tty, const u8 *cp,
88962306a36Sopenharmony_ci			    const u8 *fp, size_t count)
89062306a36Sopenharmony_ci{
89162306a36Sopenharmony_ci	struct can327 *elm = tty->disc_data;
89262306a36Sopenharmony_ci	size_t first_new_char_idx;
89362306a36Sopenharmony_ci
89462306a36Sopenharmony_ci	if (elm->uart_side_failure)
89562306a36Sopenharmony_ci		return;
89662306a36Sopenharmony_ci
89762306a36Sopenharmony_ci	spin_lock_bh(&elm->lock);
89862306a36Sopenharmony_ci
89962306a36Sopenharmony_ci	/* Store old rxfill, so can327_parse_rxbuf() will have
90062306a36Sopenharmony_ci	 * the option of skipping already checked characters.
90162306a36Sopenharmony_ci	 */
90262306a36Sopenharmony_ci	first_new_char_idx = elm->rxfill;
90362306a36Sopenharmony_ci
90462306a36Sopenharmony_ci	while (count--) {
90562306a36Sopenharmony_ci		if (elm->rxfill >= CAN327_SIZE_RXBUF) {
90662306a36Sopenharmony_ci			netdev_err(elm->dev,
90762306a36Sopenharmony_ci				   "Receive buffer overflowed. Bad chip or wiring? count = %zu",
90862306a36Sopenharmony_ci				   count);
90962306a36Sopenharmony_ci			goto uart_failure;
91062306a36Sopenharmony_ci		}
91162306a36Sopenharmony_ci		if (fp && *fp++) {
91262306a36Sopenharmony_ci			netdev_err(elm->dev,
91362306a36Sopenharmony_ci				   "Error in received character stream. Check your wiring.");
91462306a36Sopenharmony_ci			goto uart_failure;
91562306a36Sopenharmony_ci		}
91662306a36Sopenharmony_ci
91762306a36Sopenharmony_ci		/* Ignore NUL characters, which the PIC microcontroller may
91862306a36Sopenharmony_ci		 * inadvertently insert due to a known hardware bug.
91962306a36Sopenharmony_ci		 * See ELM327 documentation, which refers to a Microchip PIC
92062306a36Sopenharmony_ci		 * bug description.
92162306a36Sopenharmony_ci		 */
92262306a36Sopenharmony_ci		if (*cp) {
92362306a36Sopenharmony_ci			/* Check for stray characters on the UART line.
92462306a36Sopenharmony_ci			 * Likely caused by bad hardware.
92562306a36Sopenharmony_ci			 */
92662306a36Sopenharmony_ci			if (!can327_is_valid_rx_char(*cp)) {
92762306a36Sopenharmony_ci				netdev_err(elm->dev,
92862306a36Sopenharmony_ci					   "Received illegal character %02x.\n",
92962306a36Sopenharmony_ci					   *cp);
93062306a36Sopenharmony_ci				goto uart_failure;
93162306a36Sopenharmony_ci			}
93262306a36Sopenharmony_ci
93362306a36Sopenharmony_ci			elm->rxbuf[elm->rxfill++] = *cp;
93462306a36Sopenharmony_ci		}
93562306a36Sopenharmony_ci
93662306a36Sopenharmony_ci		cp++;
93762306a36Sopenharmony_ci	}
93862306a36Sopenharmony_ci
93962306a36Sopenharmony_ci	can327_parse_rxbuf(elm, first_new_char_idx);
94062306a36Sopenharmony_ci	spin_unlock_bh(&elm->lock);
94162306a36Sopenharmony_ci
94262306a36Sopenharmony_ci	return;
94362306a36Sopenharmony_ciuart_failure:
94462306a36Sopenharmony_ci	can327_uart_side_failure(elm);
94562306a36Sopenharmony_ci	spin_unlock_bh(&elm->lock);
94662306a36Sopenharmony_ci}
94762306a36Sopenharmony_ci
94862306a36Sopenharmony_ci/* Write out remaining transmit buffer.
94962306a36Sopenharmony_ci * Scheduled when TTY is writable.
95062306a36Sopenharmony_ci */
95162306a36Sopenharmony_cistatic void can327_ldisc_tx_worker(struct work_struct *work)
95262306a36Sopenharmony_ci{
95362306a36Sopenharmony_ci	struct can327 *elm = container_of(work, struct can327, tx_work);
95462306a36Sopenharmony_ci	ssize_t written;
95562306a36Sopenharmony_ci
95662306a36Sopenharmony_ci	if (elm->uart_side_failure)
95762306a36Sopenharmony_ci		return;
95862306a36Sopenharmony_ci
95962306a36Sopenharmony_ci	spin_lock_bh(&elm->lock);
96062306a36Sopenharmony_ci
96162306a36Sopenharmony_ci	if (elm->txleft) {
96262306a36Sopenharmony_ci		written = elm->tty->ops->write(elm->tty, elm->txhead,
96362306a36Sopenharmony_ci					       elm->txleft);
96462306a36Sopenharmony_ci		if (written < 0) {
96562306a36Sopenharmony_ci			netdev_err(elm->dev, "Failed to write to tty %s.\n",
96662306a36Sopenharmony_ci				   elm->tty->name);
96762306a36Sopenharmony_ci			can327_uart_side_failure(elm);
96862306a36Sopenharmony_ci
96962306a36Sopenharmony_ci			spin_unlock_bh(&elm->lock);
97062306a36Sopenharmony_ci			return;
97162306a36Sopenharmony_ci		}
97262306a36Sopenharmony_ci
97362306a36Sopenharmony_ci		elm->txleft -= written;
97462306a36Sopenharmony_ci		elm->txhead += written;
97562306a36Sopenharmony_ci	}
97662306a36Sopenharmony_ci
97762306a36Sopenharmony_ci	if (!elm->txleft)
97862306a36Sopenharmony_ci		clear_bit(TTY_DO_WRITE_WAKEUP, &elm->tty->flags);
97962306a36Sopenharmony_ci
98062306a36Sopenharmony_ci	spin_unlock_bh(&elm->lock);
98162306a36Sopenharmony_ci}
98262306a36Sopenharmony_ci
98362306a36Sopenharmony_ci/* Called by the driver when there's room for more data. */
98462306a36Sopenharmony_cistatic void can327_ldisc_tx_wakeup(struct tty_struct *tty)
98562306a36Sopenharmony_ci{
98662306a36Sopenharmony_ci	struct can327 *elm = tty->disc_data;
98762306a36Sopenharmony_ci
98862306a36Sopenharmony_ci	schedule_work(&elm->tx_work);
98962306a36Sopenharmony_ci}
99062306a36Sopenharmony_ci
99162306a36Sopenharmony_ci/* ELM327 can only handle bitrates that are integer divisors of 500 kHz,
99262306a36Sopenharmony_ci * or 7/8 of that. Divisors are 1 to 64.
99362306a36Sopenharmony_ci * Currently we don't implement support for 7/8 rates.
99462306a36Sopenharmony_ci */
99562306a36Sopenharmony_cistatic const u32 can327_bitrate_const[] = {
99662306a36Sopenharmony_ci	7812,  7936,  8064,  8196,   8333,   8474,   8620,   8771,
99762306a36Sopenharmony_ci	8928,  9090,  9259,  9433,   9615,   9803,   10000,  10204,
99862306a36Sopenharmony_ci	10416, 10638, 10869, 11111,  11363,  11627,  11904,  12195,
99962306a36Sopenharmony_ci	12500, 12820, 13157, 13513,  13888,  14285,  14705,  15151,
100062306a36Sopenharmony_ci	15625, 16129, 16666, 17241,  17857,  18518,  19230,  20000,
100162306a36Sopenharmony_ci	20833, 21739, 22727, 23809,  25000,  26315,  27777,  29411,
100262306a36Sopenharmony_ci	31250, 33333, 35714, 38461,  41666,  45454,  50000,  55555,
100362306a36Sopenharmony_ci	62500, 71428, 83333, 100000, 125000, 166666, 250000, 500000
100462306a36Sopenharmony_ci};
100562306a36Sopenharmony_ci
100662306a36Sopenharmony_cistatic int can327_ldisc_open(struct tty_struct *tty)
100762306a36Sopenharmony_ci{
100862306a36Sopenharmony_ci	struct net_device *dev;
100962306a36Sopenharmony_ci	struct can327 *elm;
101062306a36Sopenharmony_ci	int err;
101162306a36Sopenharmony_ci
101262306a36Sopenharmony_ci	if (!capable(CAP_NET_ADMIN))
101362306a36Sopenharmony_ci		return -EPERM;
101462306a36Sopenharmony_ci
101562306a36Sopenharmony_ci	if (!tty->ops->write)
101662306a36Sopenharmony_ci		return -EOPNOTSUPP;
101762306a36Sopenharmony_ci
101862306a36Sopenharmony_ci	dev = alloc_candev(sizeof(struct can327), 0);
101962306a36Sopenharmony_ci	if (!dev)
102062306a36Sopenharmony_ci		return -ENFILE;
102162306a36Sopenharmony_ci	elm = netdev_priv(dev);
102262306a36Sopenharmony_ci
102362306a36Sopenharmony_ci	/* Configure TTY interface */
102462306a36Sopenharmony_ci	tty->receive_room = 65536; /* We don't flow control */
102562306a36Sopenharmony_ci	spin_lock_init(&elm->lock);
102662306a36Sopenharmony_ci	INIT_WORK(&elm->tx_work, can327_ldisc_tx_worker);
102762306a36Sopenharmony_ci
102862306a36Sopenharmony_ci	/* Configure CAN metadata */
102962306a36Sopenharmony_ci	elm->can.bitrate_const = can327_bitrate_const;
103062306a36Sopenharmony_ci	elm->can.bitrate_const_cnt = ARRAY_SIZE(can327_bitrate_const);
103162306a36Sopenharmony_ci	elm->can.ctrlmode_supported = CAN_CTRLMODE_LISTENONLY;
103262306a36Sopenharmony_ci
103362306a36Sopenharmony_ci	/* Configure netdev interface */
103462306a36Sopenharmony_ci	elm->dev = dev;
103562306a36Sopenharmony_ci	dev->netdev_ops = &can327_netdev_ops;
103662306a36Sopenharmony_ci	dev->ethtool_ops = &can327_ethtool_ops;
103762306a36Sopenharmony_ci
103862306a36Sopenharmony_ci	/* Mark ldisc channel as alive */
103962306a36Sopenharmony_ci	elm->tty = tty;
104062306a36Sopenharmony_ci	tty->disc_data = elm;
104162306a36Sopenharmony_ci
104262306a36Sopenharmony_ci	/* Let 'er rip */
104362306a36Sopenharmony_ci	err = register_candev(elm->dev);
104462306a36Sopenharmony_ci	if (err) {
104562306a36Sopenharmony_ci		free_candev(elm->dev);
104662306a36Sopenharmony_ci		return err;
104762306a36Sopenharmony_ci	}
104862306a36Sopenharmony_ci
104962306a36Sopenharmony_ci	netdev_info(elm->dev, "can327 on %s.\n", tty->name);
105062306a36Sopenharmony_ci
105162306a36Sopenharmony_ci	return 0;
105262306a36Sopenharmony_ci}
105362306a36Sopenharmony_ci
105462306a36Sopenharmony_ci/* Close down a can327 channel.
105562306a36Sopenharmony_ci * This means flushing out any pending queues, and then returning.
105662306a36Sopenharmony_ci * This call is serialized against other ldisc functions:
105762306a36Sopenharmony_ci * Once this is called, no other ldisc function of ours is entered.
105862306a36Sopenharmony_ci *
105962306a36Sopenharmony_ci * We also use this function for a hangup event.
106062306a36Sopenharmony_ci */
106162306a36Sopenharmony_cistatic void can327_ldisc_close(struct tty_struct *tty)
106262306a36Sopenharmony_ci{
106362306a36Sopenharmony_ci	struct can327 *elm = tty->disc_data;
106462306a36Sopenharmony_ci
106562306a36Sopenharmony_ci	/* unregister_netdev() calls .ndo_stop() so we don't have to. */
106662306a36Sopenharmony_ci	unregister_candev(elm->dev);
106762306a36Sopenharmony_ci
106862306a36Sopenharmony_ci	/* Give UART one final chance to flush.
106962306a36Sopenharmony_ci	 * No need to clear TTY_DO_WRITE_WAKEUP since .write_wakeup() is
107062306a36Sopenharmony_ci	 * serialised against .close() and will not be called once we return.
107162306a36Sopenharmony_ci	 */
107262306a36Sopenharmony_ci	flush_work(&elm->tx_work);
107362306a36Sopenharmony_ci
107462306a36Sopenharmony_ci	/* Mark channel as dead */
107562306a36Sopenharmony_ci	spin_lock_bh(&elm->lock);
107662306a36Sopenharmony_ci	tty->disc_data = NULL;
107762306a36Sopenharmony_ci	elm->tty = NULL;
107862306a36Sopenharmony_ci	spin_unlock_bh(&elm->lock);
107962306a36Sopenharmony_ci
108062306a36Sopenharmony_ci	netdev_info(elm->dev, "can327 off %s.\n", tty->name);
108162306a36Sopenharmony_ci
108262306a36Sopenharmony_ci	free_candev(elm->dev);
108362306a36Sopenharmony_ci}
108462306a36Sopenharmony_ci
108562306a36Sopenharmony_cistatic int can327_ldisc_ioctl(struct tty_struct *tty, unsigned int cmd,
108662306a36Sopenharmony_ci			      unsigned long arg)
108762306a36Sopenharmony_ci{
108862306a36Sopenharmony_ci	struct can327 *elm = tty->disc_data;
108962306a36Sopenharmony_ci	unsigned int tmp;
109062306a36Sopenharmony_ci
109162306a36Sopenharmony_ci	switch (cmd) {
109262306a36Sopenharmony_ci	case SIOCGIFNAME:
109362306a36Sopenharmony_ci		tmp = strnlen(elm->dev->name, IFNAMSIZ - 1) + 1;
109462306a36Sopenharmony_ci		if (copy_to_user((void __user *)arg, elm->dev->name, tmp))
109562306a36Sopenharmony_ci			return -EFAULT;
109662306a36Sopenharmony_ci		return 0;
109762306a36Sopenharmony_ci
109862306a36Sopenharmony_ci	case SIOCSIFHWADDR:
109962306a36Sopenharmony_ci		return -EINVAL;
110062306a36Sopenharmony_ci
110162306a36Sopenharmony_ci	default:
110262306a36Sopenharmony_ci		return tty_mode_ioctl(tty, cmd, arg);
110362306a36Sopenharmony_ci	}
110462306a36Sopenharmony_ci}
110562306a36Sopenharmony_ci
110662306a36Sopenharmony_cistatic struct tty_ldisc_ops can327_ldisc = {
110762306a36Sopenharmony_ci	.owner = THIS_MODULE,
110862306a36Sopenharmony_ci	.name = KBUILD_MODNAME,
110962306a36Sopenharmony_ci	.num = N_CAN327,
111062306a36Sopenharmony_ci	.receive_buf = can327_ldisc_rx,
111162306a36Sopenharmony_ci	.write_wakeup = can327_ldisc_tx_wakeup,
111262306a36Sopenharmony_ci	.open = can327_ldisc_open,
111362306a36Sopenharmony_ci	.close = can327_ldisc_close,
111462306a36Sopenharmony_ci	.ioctl = can327_ldisc_ioctl,
111562306a36Sopenharmony_ci};
111662306a36Sopenharmony_ci
111762306a36Sopenharmony_cistatic int __init can327_init(void)
111862306a36Sopenharmony_ci{
111962306a36Sopenharmony_ci	int status;
112062306a36Sopenharmony_ci
112162306a36Sopenharmony_ci	status = tty_register_ldisc(&can327_ldisc);
112262306a36Sopenharmony_ci	if (status)
112362306a36Sopenharmony_ci		pr_err("Can't register line discipline\n");
112462306a36Sopenharmony_ci
112562306a36Sopenharmony_ci	return status;
112662306a36Sopenharmony_ci}
112762306a36Sopenharmony_ci
112862306a36Sopenharmony_cistatic void __exit can327_exit(void)
112962306a36Sopenharmony_ci{
113062306a36Sopenharmony_ci	/* This will only be called when all channels have been closed by
113162306a36Sopenharmony_ci	 * userspace - tty_ldisc.c takes care of the module's refcount.
113262306a36Sopenharmony_ci	 */
113362306a36Sopenharmony_ci	tty_unregister_ldisc(&can327_ldisc);
113462306a36Sopenharmony_ci}
113562306a36Sopenharmony_ci
113662306a36Sopenharmony_cimodule_init(can327_init);
113762306a36Sopenharmony_cimodule_exit(can327_exit);
113862306a36Sopenharmony_ci
113962306a36Sopenharmony_ciMODULE_ALIAS_LDISC(N_CAN327);
114062306a36Sopenharmony_ciMODULE_DESCRIPTION("ELM327 based CAN interface");
114162306a36Sopenharmony_ciMODULE_LICENSE("GPL");
114262306a36Sopenharmony_ciMODULE_AUTHOR("Max Staudt <max@enpas.org>");
1143