text: /* Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
   * Use of this source code is governed by a BSD-style license that can be
   * found in the LICENSE file.
   */
  
  /* uart.h - UART module for Chrome EC */
  
  #ifndef __CROS_EC_UART_H
  #define __CROS_EC_UART_H
  
  #include <stdarg.h>  /* For va_list */
  #include "common.h"
  #include "gpio.h"
  
  /**
   * Initialize the UART module.
   */
  void uart_init(void);
  
  /**
   * Return non-zero if UART init has completed.
   */
  int uart_init_done(void);
  
  /*
   * Output functions
   *
   * Output is buffered.  If the buffer overflows, subsequent output is
   * discarded.
   *
   * Modules should use the output functions in console.h in preference to these
   * routines, so that output can be filtered on a module-by-module basis.
   */
  
  /**
   * Put a single character to the UART, like putchar().
   *
   * @param c		Character to put
   * @return EC_SUCCESS, or non-zero if output was truncated.
   */
  int uart_putc(int c);
  
  /**
   * Put a null-terminated string to the UART, like fputs().
   *
   * @return EC_SUCCESS, or non-zero if output was truncated.
   */
  int uart_puts(const char *outstr);
  
  /**
   * Print formatted output to the UART, like printf().
   *
   * See printf.h for valid formatting codes.
   *
   * @return EC_SUCCESS, or non-zero if output was truncated.
   */
  int uart_printf(const char *format, ...);
  
  /**
   * Print formatted output to the UART, like vprintf().
   *
   * See printf.h for valid formatting codes.
   *
   * @return EC_SUCCESS, or non-zero if output was truncated.
   */
  int uart_vprintf(const char *format, va_list args);
  
  /**
   * Flush output.  Blocks until UART has transmitted all output.
   */
  void uart_flush_output(void);
  
  /*
   * Input functions
   *
   * Input is buffered.  If the buffer overflows, the oldest input in
   * the buffer is discarded to make room for the new input.
   *
   * Input lines may be terminated by CR ('\r'), LF ('\n'), or CRLF; all
   * are translated to newline.
   */
  
  /**
   * Read a single character of input, similar to fgetc().
   *
   * @return the character, or -1 if no input waiting.
   */
  int uart_getc(void);
  
  /*
   * Hardware UART driver functions
   */
  
  /**
   * Flush the transmit FIFO.
   */
  void uart_tx_flush(void);
  
  /**
   * Return non-zero if there is room to transmit a character immediately.
   */
  int uart_tx_ready(void);
  
  /**
   * Return non-zero if a transmit is in progress.
   */
  int uart_tx_in_progress(void);
  
  /**
   * Return non-zero if UART is ready to start a DMA transfer.
   */
  int uart_tx_dma_ready(void);
  
  /**
   * Start a UART transmit DMA transfer
   *
   * @param src		Pointer to data to send
   * @param len		Length of transfer in bytes
   */
  void uart_tx_dma_start(const char *src, int len);
  
  /**
   * Return non-zero if the UART has a character available to read.
   */
  int uart_rx_available(void);
  
  /**
   * Start a UART receive DMA transfer.
   *
   * DMA will be configured in circular buffer mode, so received characters
   * will be stored into the buffer continuously.
   *
   * @param dest		Pointer to destination buffer
   * @param len		Length of buffer in bytes
   */
  void uart_rx_dma_start(char *dest, int len);
  
  /**
   * Return the head of the receive DMA transfer buffer
   *
   * This is the next offset in the buffer which will receive a character, and
   * will be from 0..(len-1) where len is the buffer length passed to
   * uart_rx_dma_start().
   */
  int uart_rx_dma_head(void);
  
  /**
   * Send a character to the UART data register.
   *
   * If the transmit FIFO is full, blocks until there is space.
   *
   * @param c		Character to send.
   */
  void uart_write_char(char c);
  
  /**
   * Read one char from the UART data register.
   *
   * @return		The character read.
   */
  int uart_read_char(void);
  
  /**
   * Re-enable the UART transmit interrupt.
   *
   * This also forces triggering a UART interrupt, if the transmit interrupt was
   * disabled.
   */
  void uart_tx_start(void);
  
  /**
   * Disable the UART transmit interrupt.
   */
  void uart_tx_stop(void);
  
  /**
   * Helper for processing UART input.
   *
   * Reads the input FIFO until empty.  Intended to be called from the driver
   * interrupt handler.
   */
  void uart_process_input(void);
  
  /**
   * Helper for processing UART output.
   *
   * Fills the output FIFO until the transmit buffer is empty or the FIFO full.
   * Intended to be called from the driver interrupt handler.
   */
  void uart_process_output(void);
  
  /**
   * Return boolean expressing whether UART buffer is empty or not.
   */
  int uart_buffer_empty(void);
  
  /**
   * Disable the EC console UART and convert the UART RX pin to a generic GPIO
   * with an edge detect interrupt.
   */
  void uart_enter_dsleep(void);
  
  /**
   * Enable the EC console UART after a uart_enter_dsleep().
   */
  void uart_exit_dsleep(void);
  
  #ifdef CONFIG_LOW_POWER_IDLE
  /**
   * Interrupt handler for UART RX pin transition in deep sleep.
   *
   * @param signal	Signal which triggered the interrupt.
   */
  void uart_deepsleep_interrupt(enum gpio_signal signal);
  #else
  static inline void uart_deepsleep_interrupt(enum gpio_signal signal) { }
  #endif /* !CONFIG_LOW_POWER_IDLE */
  
  #if defined(HAS_TASK_CONSOLE) && defined(CONFIG_FORCE_CONSOLE_RESUME)
  /**
   * Enable/Disable the UART controller low-power mode wake-up capability.
   *
   * @param enable  1 to enable wake-up, 0 to disable it.
   */
  void uart_enable_wakeup(int enable);
  #elif !defined(CHIP_FAMILY_NPCX5)
  static inline void uart_enable_wakeup(int enable) {}
  #endif
  
  #ifdef CONFIG_UART_INPUT_FILTER
  /**
   * Application-specific input filter, which takes the next input character as
   * a parameter.
   *
   * Return 0 to allow the character to be handled by the console, non-zero if
   * the character was handled by the filter.
   */
  int uart_input_filter(int c);
  #endif
  
  /*
   * COMx functions
   */
  
  /**
   * Enable COMx interrupts
   */
  void uart_comx_enable(void);
  
  /**
   * Return non-zero if ok to put a character via uart_comx_putc().
   */
  int uart_comx_putc_ok(void);
  
  /**
   * Write a character to the COMx UART interface.
   */
  void uart_comx_putc(int c);
  
  /*
   * Functions for pad switching UART, only defined on some chips (npcx), and
   * if CONFIG_UART_PAD_SWITCH is enabled.
   */
  enum uart_pad {
  	UART_DEFAULT_PAD = 0,
  	UART_ALTERNATE_PAD = 1,
  };
  
  /**
   * Reset UART pad to default pad, so that a panic information can be printed
   * on the EC console.
   */
  void uart_reset_default_pad_panic(void);
  
  /**
   * Specialized function to write then read data on UART alternate pad.
   * The transfer may be interrupted at any time if data is received on the main
   * pad.
   *
   * @param tx		Data to be sent
   * @param tx_len	Length of data to be sent
   * @param rx		Buffer to receive data
   * @param rx_len	Receive buffer length
   * @param timeout_us	Timeout in microseconds for the transaction to complete.
   *
   * @return The number of bytes read back (indicates a timeout if != rx_len).
   *         - -EC_ERROR_BUSY if the alternate pad cannot be used (e.g. default
   *           pad is currently being used), or if the transfer was interrupted.
   *         - -EC_ERROR_TIMEOUT in case tx_len bytes cannot be written in the
   *           time specified in timeout_us.
   */
  int uart_alt_pad_write_read(uint8_t *tx, int tx_len, uint8_t *rx, int rx_len,
  			int timeout_us);
  
  /**
   * Interrupt handler for default UART RX pin transition when UART is switched
   * to alternate pad.
   *
   * @param signal	Signal which triggered the interrupt.
   */
  void uart_default_pad_rx_interrupt(enum gpio_signal signal);
  
  #endif  /* __CROS_EC_UART_H */
  