/******************************************************************************
 * Copyright (c) 2007, 2012, 2013 IBM Corporation
 * All rights reserved.
 * This program and the accompanying materials
 * are made available under the terms of the BSD License
 * which accompanies this distribution, and is available at
 * http://www.opensource.org/licenses/bsd-license.php
 *
 * Contributors:
 *     IBM Corporation - initial implementation
 *****************************************************************************/
/*
 * Definitions for OHCI Controller
 *
 * USB on the PowerStation:
 *   ohci0 - port 0     -> not connected
 *   ohci0 - port 1 - 2 -> Internal connector (J60_USBINT)
 *   ohci1 - port 0     -> not connected
 *   ohci1 - port 1 - 2 -> External connector (J10_USBEXT)
 */

#ifndef USB_OHCI_H
#define USB_OHCI_H

#include <stdint.h>

struct ohci_regs {
	uint32_t rev;
	uint32_t control;
	uint32_t cmd_status;
	uint32_t intr_status;
	uint32_t intr_enable;
	uint32_t intr_disable;
	uint32_t hcca;
	uint32_t period_curr_ed;
	uint32_t cntl_head_ed;
	uint32_t cntl_curr_ed;
	uint32_t bulk_head_ed;
	uint32_t bulk_curr_ed;
	uint32_t done_head;
	uint32_t fm_interval;
	uint32_t fm_remaining;
	uint32_t fm_num;
	uint32_t period_start;
	uint32_t ls_threshold;
	uint32_t rh_desc_a;
	uint32_t rh_desc_b;
	uint32_t rh_status;
	uint32_t rh_ps[5];
} __attribute__((packed, aligned(4)));

#define EDA_FADDR(x)     ((x & 0x7F))
#define EDA_EP(x)        ((x & 0x0F) << 7)
#define EDA_DIR_OUT      (1 << 11)
#define EDA_DIR_IN       (1 << 12)
#define EDA_LOW_SPEED    (1 << 13)
#define EDA_SKIP         (1 << 14)
#define EDA_SKIP_LE      (0x400000) /* avoiding conversions */
#define EDA_FORMAT_ISO   (1 << 15)
#define EDA_MPS(x)       ((x & 0x7FF) << 16)

#define EDA_HEADP_MASK    (0xFFFFFFFC)
#define EDA_HEADP_MASK_LE (cpu_to_le32(EDA_HEADP_MASK))
#define EDA_HEADP_HALTED  (0x1)
#define EDA_HEADP_CARRY   (0x2)

struct ohci_ed {
	uint32_t attr;
	uint32_t tailp;
	uint32_t headp;
	uint32_t next_ed;
} __attribute__((packed));

#define TDA_DONE         (1 << 17)
#define TDA_ROUNDING     (1 << 18)
#define TDA_DP_SETUP     (0 << 19)
#define TDA_DP_OUT       (1 << 19)
#define TDA_DP_IN        (1 << 20)
#define TDA_DI_NO        (0x7 << 21)
#define TDA_TOGGLE_DATA0 (0x02000000)
#define TDA_TOGGLE_DATA1 (0x03000000)
#define TDA_CC           (0xF << 28)

#define TDA_ERROR(x)         ((x) * -1)

/* Table 4-7: Completion Codes */
const char *tda_cc_error[] = {
#define USB_NOERROR TDA_ERROR(0)
	"NOERROR",
	"CRC",
	"BITSTUFFING",
	"DATATOGGLEMISMATCH",
#define USB_STALL TDA_ERROR(4)
	"STALL",
	"DEVICENOTRESPONDING",
	"PIDCHECKFAILURE",
	"UNEXPECTEDPID",
	"DATAOVERRUN",
	"DATAUNDERRUN",
	"reserved",
	"reserved",
	"BUFFEROVERRUN",
	"BUFFERUNDERRUN",
	"NOT ACCESSED",
	"NOT ACCESSED",
};

struct ohci_td {
	uint32_t attr;
	uint32_t cbp;
	uint32_t next_td;
	uint32_t be;
} __attribute__((packed));

#define	HCCA_SIZE	256
#define	HCCA_ALIGN	(HCCA_SIZE - 1)
#define HCCA_INTR_NUM   32
struct ohci_hcca {
	uint32_t  intr_table[HCCA_INTR_NUM];
	uint16_t  frame_num;
	uint16_t  pad1;
	uint32_t  done_head;
	uint32_t  reserved[120];
} __attribute__((packed));

struct ohci_pipe {
	struct ohci_ed  ed; /* has to be aligned at 16 byte address*/
	struct usb_pipe pipe;
	struct ohci_td  *td;
	void *buf;
	long ed_phys;
	long td_phys;
	long buf_phys;
	uint32_t buflen;
	uint32_t count;
	uint8_t pad[0];
}__attribute__((packed));

#define OHCI_PIPE_POOL_SIZE 4096
#define OHCI_MAX_TDS        256 /* supports 16k buffers, i.e. 64 * 256 */
#define OHCI_MAX_BULK_SIZE  4096

struct ohci_hcd {
	struct ohci_hcca *hcca;
	struct ohci_regs *regs;
	struct usb_hcd_dev *hcidev;
	struct usb_pipe *freelist;
	struct usb_pipe *end;
	struct usb_dev rhdev;
	long hcca_phys;
	void *pool;
	long pool_phys;
};

#define OHCI_CTRL_CBSR  (3 << 0)
#define OHCI_CTRL_PLE   (1 << 2)
#define OHCI_CTRL_CLE   (1 << 4)
#define OHCI_CTRL_BLE   (1 << 5)
#define OHCI_CTRL_HCFS  (3 << 6)
#define OHCI_USB_RESET   (0 << 6)
#define OHCI_USB_OPER    (2 << 6)
#define OHCI_USB_SUSPEND (3 << 6)
#define OHCI_CTRL_RWC   (1 << 9)

/* OHCI Command Status */
#define OHCI_CMD_STATUS_HCR   (1 << 0)
#define OHCI_CMD_STATUS_CLF   (1 << 1)
#define OHCI_CMD_STATUS_BLF   (1 << 2)

/* OHCI Interrupt status */
#define OHCI_INTR_STATUS_WD   (1 << 1)

/* Root Hub Descriptor A bits */
#define RHDA_NDP                 (0xFF)
#define RHDA_PSM_INDIVIDUAL      (1 << 8)
#define RHDA_NPS_ENABLE          (1 << 9)
#define RHDA_DT                  (1 << 10)
#define RHDA_OCPM_PERPORT        (1 << 11)
#define RHDA_NOCP_ENABLE         (1 << 12)

/* Root Hub Descriptor B bits */
#define RHDB_PPCM_PORT_POWER     (0xFFFE)
#define RHDB_PPCM_GLOBAL_POWER   (0x0000)

#define RH_STATUS_LPSC           (1 << 16)
#define RH_STATUS_OCIC           (1 << 17)
#define RH_STATUS_CREW           (1 << 31)

#define RH_PS_CCS                (1 <<  0)
#define RH_PS_PES                (1 <<  1)
#define RH_PS_PSS                (1 <<  2)
#define RH_PS_POCI               (1 <<  3)
#define RH_PS_PRS                (1 <<  4)
#define RH_PS_PPS                (1 <<  8)
#define RH_PS_LSDA               (1 <<  9)

#define RH_PS_CSC                (1 << 16)
#define RH_PS_PESC               (1 << 17)
#define RH_PS_PSSC               (1 << 18)
#define RH_PS_OCIC               (1 << 19)
#define RH_PS_PRSC               (1 << 20)

/*********************************************************************/
/* Values for USB Frame Timing                                       */
/* One USB frame (1ms) consists of 12000 bit-times as clock is 12MHz */
/* controller can be adjusted for performance optimization           */
/* We use standard values (OHCI spec 6.3.1, 5.1.1.4,  5.4, 7.3.4)    */
/*********************************************************************/
#define FRAME_INTERVAL		(((((11999 - 210) * 6) / 7) << 16) | 11999)
#define PERIODIC_START		((11999 * 9) / 10)


static inline struct ohci_ed *ohci_pipe_get_ed(struct usb_pipe *pipe);
static inline long ohci_pipe_get_ed_phys(struct usb_pipe *pipe);
static int ohci_alloc_pipe_pool(struct ohci_hcd *ohcd);

#endif	/* USB_OHCI_H */
