linux/drivers/usb/renesas_usbhs/pipe.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-1.0+
   2/*
   3 * Renesas USB driver
   4 *
   5 * Copyright (C) 2011 Renesas Solutions Corp.
   6 * Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>
   7 */
   8#include <linux/delay.h>
   9#include <linux/slab.h>
  10#include "common.h"
  11#include "pipe.h"
  12
  13/*
  14 *              macros
  15 */
  16#define usbhsp_addr_offset(p)   ((usbhs_pipe_number(p) - 1) * 2)
  17
  18#define usbhsp_flags_set(p, f)  ((p)->flags |=  USBHS_PIPE_FLAGS_##f)
  19#define usbhsp_flags_clr(p, f)  ((p)->flags &= ~USBHS_PIPE_FLAGS_##f)
  20#define usbhsp_flags_has(p, f)  ((p)->flags &   USBHS_PIPE_FLAGS_##f)
  21#define usbhsp_flags_init(p)    do {(p)->flags = 0; } while (0)
  22
  23/*
  24 * for debug
  25 */
  26static char *usbhsp_pipe_name[] = {
  27        [USB_ENDPOINT_XFER_CONTROL]     = "DCP",
  28        [USB_ENDPOINT_XFER_BULK]        = "BULK",
  29        [USB_ENDPOINT_XFER_INT]         = "INT",
  30        [USB_ENDPOINT_XFER_ISOC]        = "ISO",
  31};
  32
  33char *usbhs_pipe_name(struct usbhs_pipe *pipe)
  34{
  35        return usbhsp_pipe_name[usbhs_pipe_type(pipe)];
  36}
  37
  38static struct renesas_usbhs_driver_pipe_config
  39*usbhsp_get_pipe_config(struct usbhs_priv *priv, int pipe_num)
  40{
  41        struct renesas_usbhs_driver_pipe_config *pipe_configs =
  42                                        usbhs_get_dparam(priv, pipe_configs);
  43
  44        return &pipe_configs[pipe_num];
  45}
  46
  47/*
  48 *              DCPCTR/PIPEnCTR functions
  49 */
  50static void usbhsp_pipectrl_set(struct usbhs_pipe *pipe, u16 mask, u16 val)
  51{
  52        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
  53        int offset = usbhsp_addr_offset(pipe);
  54
  55        if (usbhs_pipe_is_dcp(pipe))
  56                usbhs_bset(priv, DCPCTR, mask, val);
  57        else
  58                usbhs_bset(priv, PIPEnCTR + offset, mask, val);
  59}
  60
  61static u16 usbhsp_pipectrl_get(struct usbhs_pipe *pipe)
  62{
  63        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
  64        int offset = usbhsp_addr_offset(pipe);
  65
  66        if (usbhs_pipe_is_dcp(pipe))
  67                return usbhs_read(priv, DCPCTR);
  68        else
  69                return usbhs_read(priv, PIPEnCTR + offset);
  70}
  71
  72/*
  73 *              DCP/PIPE functions
  74 */
  75static void __usbhsp_pipe_xxx_set(struct usbhs_pipe *pipe,
  76                                  u16 dcp_reg, u16 pipe_reg,
  77                                  u16 mask, u16 val)
  78{
  79        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
  80
  81        if (usbhs_pipe_is_dcp(pipe))
  82                usbhs_bset(priv, dcp_reg, mask, val);
  83        else
  84                usbhs_bset(priv, pipe_reg, mask, val);
  85}
  86
  87static u16 __usbhsp_pipe_xxx_get(struct usbhs_pipe *pipe,
  88                                 u16 dcp_reg, u16 pipe_reg)
  89{
  90        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
  91
  92        if (usbhs_pipe_is_dcp(pipe))
  93                return usbhs_read(priv, dcp_reg);
  94        else
  95                return usbhs_read(priv, pipe_reg);
  96}
  97
  98/*
  99 *              DCPCFG/PIPECFG functions
 100 */
 101static void usbhsp_pipe_cfg_set(struct usbhs_pipe *pipe, u16 mask, u16 val)
 102{
 103        __usbhsp_pipe_xxx_set(pipe, DCPCFG, PIPECFG, mask, val);
 104}
 105
 106static u16 usbhsp_pipe_cfg_get(struct usbhs_pipe *pipe)
 107{
 108        return __usbhsp_pipe_xxx_get(pipe, DCPCFG, PIPECFG);
 109}
 110
 111/*
 112 *              PIPEnTRN/PIPEnTRE functions
 113 */
 114static void usbhsp_pipe_trn_set(struct usbhs_pipe *pipe, u16 mask, u16 val)
 115{
 116        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
 117        struct device *dev = usbhs_priv_to_dev(priv);
 118        int num = usbhs_pipe_number(pipe);
 119        u16 reg;
 120
 121        /*
 122         * It is impossible to calculate address,
 123         * since PIPEnTRN addresses were mapped randomly.
 124         */
 125#define CASE_PIPExTRN(a)                \
 126        case 0x ## a:                   \
 127                reg = PIPE ## a ## TRN; \
 128                break;
 129
 130        switch (num) {
 131        CASE_PIPExTRN(1);
 132        CASE_PIPExTRN(2);
 133        CASE_PIPExTRN(3);
 134        CASE_PIPExTRN(4);
 135        CASE_PIPExTRN(5);
 136        CASE_PIPExTRN(B);
 137        CASE_PIPExTRN(C);
 138        CASE_PIPExTRN(D);
 139        CASE_PIPExTRN(E);
 140        CASE_PIPExTRN(F);
 141        CASE_PIPExTRN(9);
 142        CASE_PIPExTRN(A);
 143        default:
 144                dev_err(dev, "unknown pipe (%d)\n", num);
 145                return;
 146        }
 147        __usbhsp_pipe_xxx_set(pipe, 0, reg, mask, val);
 148}
 149
 150static void usbhsp_pipe_tre_set(struct usbhs_pipe *pipe, u16 mask, u16 val)
 151{
 152        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
 153        struct device *dev = usbhs_priv_to_dev(priv);
 154        int num = usbhs_pipe_number(pipe);
 155        u16 reg;
 156
 157        /*
 158         * It is impossible to calculate address,
 159         * since PIPEnTRE addresses were mapped randomly.
 160         */
 161#define CASE_PIPExTRE(a)                        \
 162        case 0x ## a:                           \
 163                reg = PIPE ## a ## TRE;         \
 164                break;
 165
 166        switch (num) {
 167        CASE_PIPExTRE(1);
 168        CASE_PIPExTRE(2);
 169        CASE_PIPExTRE(3);
 170        CASE_PIPExTRE(4);
 171        CASE_PIPExTRE(5);
 172        CASE_PIPExTRE(B);
 173        CASE_PIPExTRE(C);
 174        CASE_PIPExTRE(D);
 175        CASE_PIPExTRE(E);
 176        CASE_PIPExTRE(F);
 177        CASE_PIPExTRE(9);
 178        CASE_PIPExTRE(A);
 179        default:
 180                dev_err(dev, "unknown pipe (%d)\n", num);
 181                return;
 182        }
 183
 184        __usbhsp_pipe_xxx_set(pipe, 0, reg, mask, val);
 185}
 186
 187/*
 188 *              PIPEBUF
 189 */
 190static void usbhsp_pipe_buf_set(struct usbhs_pipe *pipe, u16 mask, u16 val)
 191{
 192        if (usbhs_pipe_is_dcp(pipe))
 193                return;
 194
 195        __usbhsp_pipe_xxx_set(pipe, 0, PIPEBUF, mask, val);
 196}
 197
 198/*
 199 *              DCPMAXP/PIPEMAXP
 200 */
 201static void usbhsp_pipe_maxp_set(struct usbhs_pipe *pipe, u16 mask, u16 val)
 202{
 203        __usbhsp_pipe_xxx_set(pipe, DCPMAXP, PIPEMAXP, mask, val);
 204}
 205
 206/*
 207 *              pipe control functions
 208 */
 209static void usbhsp_pipe_select(struct usbhs_pipe *pipe)
 210{
 211        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
 212
 213        /*
 214         * On pipe, this is necessary before
 215         * accesses to below registers.
 216         *
 217         * PIPESEL      : usbhsp_pipe_select
 218         * PIPECFG      : usbhsp_pipe_cfg_xxx
 219         * PIPEBUF      : usbhsp_pipe_buf_xxx
 220         * PIPEMAXP     : usbhsp_pipe_maxp_xxx
 221         * PIPEPERI
 222         */
 223
 224        /*
 225         * if pipe is dcp, no pipe is selected.
 226         * it is no problem, because dcp have its register
 227         */
 228        usbhs_write(priv, PIPESEL, 0xF & usbhs_pipe_number(pipe));
 229}
 230
 231static int usbhsp_pipe_barrier(struct usbhs_pipe *pipe)
 232{
 233        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
 234        int timeout = 1024;
 235        u16 mask = usbhs_mod_is_host(priv) ? (CSSTS | PID_MASK) : PID_MASK;
 236
 237        /*
 238         * make sure....
 239         *
 240         * Modify these bits when CSSTS = 0, PID = NAK, and no pipe number is
 241         * specified by the CURPIPE bits.
 242         * When changing the setting of this bit after changing
 243         * the PID bits for the selected pipe from BUF to NAK,
 244         * check that CSSTS = 0 and PBUSY = 0.
 245         */
 246
 247        /*
 248         * CURPIPE bit = 0
 249         *
 250         * see also
 251         *  "Operation"
 252         *  - "Pipe Control"
 253         *   - "Pipe Control Registers Switching Procedure"
 254         */
 255        usbhs_write(priv, CFIFOSEL, 0);
 256        usbhs_pipe_disable(pipe);
 257
 258        do {
 259                if (!(usbhsp_pipectrl_get(pipe) & mask))
 260                        return 0;
 261
 262                udelay(10);
 263
 264        } while (timeout--);
 265
 266        return -EBUSY;
 267}
 268
 269int usbhs_pipe_is_accessible(struct usbhs_pipe *pipe)
 270{
 271        u16 val;
 272
 273        val = usbhsp_pipectrl_get(pipe);
 274        if (val & BSTS)
 275                return 0;
 276
 277        return -EBUSY;
 278}
 279
 280/*
 281 *              PID ctrl
 282 */
 283static void __usbhsp_pid_try_nak_if_stall(struct usbhs_pipe *pipe)
 284{
 285        u16 pid = usbhsp_pipectrl_get(pipe);
 286
 287        pid &= PID_MASK;
 288
 289        /*
 290         * see
 291         * "Pipe n Control Register" - "PID"
 292         */
 293        switch (pid) {
 294        case PID_STALL11:
 295                usbhsp_pipectrl_set(pipe, PID_MASK, PID_STALL10);
 296                /* fall-through */
 297        case PID_STALL10:
 298                usbhsp_pipectrl_set(pipe, PID_MASK, PID_NAK);
 299        }
 300}
 301
 302void usbhs_pipe_disable(struct usbhs_pipe *pipe)
 303{
 304        int timeout = 1024;
 305        u16 val;
 306
 307        /* see "Pipe n Control Register" - "PID" */
 308        __usbhsp_pid_try_nak_if_stall(pipe);
 309
 310        usbhsp_pipectrl_set(pipe, PID_MASK, PID_NAK);
 311
 312        do {
 313                val  = usbhsp_pipectrl_get(pipe);
 314                val &= PBUSY;
 315                if (!val)
 316                        break;
 317
 318                udelay(10);
 319        } while (timeout--);
 320}
 321
 322void usbhs_pipe_enable(struct usbhs_pipe *pipe)
 323{
 324        /* see "Pipe n Control Register" - "PID" */
 325        __usbhsp_pid_try_nak_if_stall(pipe);
 326
 327        usbhsp_pipectrl_set(pipe, PID_MASK, PID_BUF);
 328}
 329
 330void usbhs_pipe_stall(struct usbhs_pipe *pipe)
 331{
 332        u16 pid = usbhsp_pipectrl_get(pipe);
 333
 334        pid &= PID_MASK;
 335
 336        /*
 337         * see
 338         * "Pipe n Control Register" - "PID"
 339         */
 340        switch (pid) {
 341        case PID_NAK:
 342                usbhsp_pipectrl_set(pipe, PID_MASK, PID_STALL10);
 343                break;
 344        case PID_BUF:
 345                usbhsp_pipectrl_set(pipe, PID_MASK, PID_STALL11);
 346                break;
 347        }
 348}
 349
 350int usbhs_pipe_is_stall(struct usbhs_pipe *pipe)
 351{
 352        u16 pid = usbhsp_pipectrl_get(pipe) & PID_MASK;
 353
 354        return (int)(pid == PID_STALL10 || pid == PID_STALL11);
 355}
 356
 357void usbhs_pipe_set_trans_count_if_bulk(struct usbhs_pipe *pipe, int len)
 358{
 359        if (!usbhs_pipe_type_is(pipe, USB_ENDPOINT_XFER_BULK))
 360                return;
 361
 362        /*
 363         * clear and disable transfer counter for IN/OUT pipe
 364         */
 365        usbhsp_pipe_tre_set(pipe, TRCLR | TRENB, TRCLR);
 366
 367        /*
 368         * Only IN direction bulk pipe can use transfer count.
 369         * Without using this function,
 370         * received data will break if it was large data size.
 371         * see PIPEnTRN/PIPEnTRE for detail
 372         */
 373        if (usbhs_pipe_is_dir_in(pipe)) {
 374                int maxp = usbhs_pipe_get_maxpacket(pipe);
 375
 376                usbhsp_pipe_trn_set(pipe, 0xffff, DIV_ROUND_UP(len, maxp));
 377                usbhsp_pipe_tre_set(pipe, TRENB, TRENB); /* enable */
 378        }
 379}
 380
 381
 382/*
 383 *              pipe setup
 384 */
 385static int usbhsp_setup_pipecfg(struct usbhs_pipe *pipe, int is_host,
 386                                int dir_in, u16 *pipecfg)
 387{
 388        u16 type = 0;
 389        u16 bfre = 0;
 390        u16 dblb = 0;
 391        u16 cntmd = 0;
 392        u16 dir = 0;
 393        u16 epnum = 0;
 394        u16 shtnak = 0;
 395        static const u16 type_array[] = {
 396                [USB_ENDPOINT_XFER_BULK] = TYPE_BULK,
 397                [USB_ENDPOINT_XFER_INT]  = TYPE_INT,
 398                [USB_ENDPOINT_XFER_ISOC] = TYPE_ISO,
 399        };
 400
 401        if (usbhs_pipe_is_dcp(pipe))
 402                return -EINVAL;
 403
 404        /*
 405         * PIPECFG
 406         *
 407         * see
 408         *  - "Register Descriptions" - "PIPECFG" register
 409         *  - "Features"  - "Pipe configuration"
 410         *  - "Operation" - "Pipe Control"
 411         */
 412
 413        /* TYPE */
 414        type = type_array[usbhs_pipe_type(pipe)];
 415
 416        /* BFRE */
 417        if (usbhs_pipe_type_is(pipe, USB_ENDPOINT_XFER_ISOC) ||
 418            usbhs_pipe_type_is(pipe, USB_ENDPOINT_XFER_BULK))
 419                bfre = 0; /* FIXME */
 420
 421        /* DBLB: see usbhs_pipe_config_update() */
 422
 423        /* CNTMD */
 424        if (usbhs_pipe_type_is(pipe, USB_ENDPOINT_XFER_BULK))
 425                cntmd = 0; /* FIXME */
 426
 427        /* DIR */
 428        if (dir_in)
 429                usbhsp_flags_set(pipe, IS_DIR_HOST);
 430
 431        if (!!is_host ^ !!dir_in)
 432                dir |= DIR_OUT;
 433
 434        if (!dir)
 435                usbhsp_flags_set(pipe, IS_DIR_IN);
 436
 437        /* SHTNAK */
 438        if (usbhs_pipe_type_is(pipe, USB_ENDPOINT_XFER_BULK) &&
 439            !dir)
 440                shtnak = SHTNAK;
 441
 442        /* EPNUM */
 443        epnum = 0; /* see usbhs_pipe_config_update() */
 444        *pipecfg = type         |
 445                   bfre         |
 446                   dblb         |
 447                   cntmd        |
 448                   dir          |
 449                   shtnak       |
 450                   epnum;
 451        return 0;
 452}
 453
 454static u16 usbhsp_setup_pipebuff(struct usbhs_pipe *pipe)
 455{
 456        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
 457        struct device *dev = usbhs_priv_to_dev(priv);
 458        int pipe_num = usbhs_pipe_number(pipe);
 459        u16 buff_size;
 460        u16 bufnmb;
 461        u16 bufnmb_cnt;
 462        struct renesas_usbhs_driver_pipe_config *pipe_config =
 463                                        usbhsp_get_pipe_config(priv, pipe_num);
 464
 465        /*
 466         * PIPEBUF
 467         *
 468         * see
 469         *  - "Register Descriptions" - "PIPEBUF" register
 470         *  - "Features"  - "Pipe configuration"
 471         *  - "Operation" - "FIFO Buffer Memory"
 472         *  - "Operation" - "Pipe Control"
 473         */
 474        buff_size = pipe_config->bufsize;
 475        bufnmb = pipe_config->bufnum;
 476
 477        /* change buff_size to register value */
 478        bufnmb_cnt = (buff_size / 64) - 1;
 479
 480        dev_dbg(dev, "pipe : %d : buff_size 0x%x: bufnmb 0x%x\n",
 481                pipe_num, buff_size, bufnmb);
 482
 483        return  (0x1f & bufnmb_cnt)     << 10 |
 484                (0xff & bufnmb)         <<  0;
 485}
 486
 487void usbhs_pipe_config_update(struct usbhs_pipe *pipe, u16 devsel,
 488                              u16 epnum, u16 maxp)
 489{
 490        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
 491        int pipe_num = usbhs_pipe_number(pipe);
 492        struct renesas_usbhs_driver_pipe_config *pipe_config =
 493                                        usbhsp_get_pipe_config(priv, pipe_num);
 494        u16 dblb = pipe_config->double_buf ? DBLB : 0;
 495
 496        if (devsel > 0xA) {
 497                struct device *dev = usbhs_priv_to_dev(priv);
 498
 499                dev_err(dev, "devsel error %d\n", devsel);
 500
 501                devsel = 0;
 502        }
 503
 504        usbhsp_pipe_barrier(pipe);
 505
 506        pipe->maxp = maxp;
 507
 508        usbhsp_pipe_select(pipe);
 509        usbhsp_pipe_maxp_set(pipe, 0xFFFF,
 510                             (devsel << 12) |
 511                             maxp);
 512
 513        if (!usbhs_pipe_is_dcp(pipe))
 514                usbhsp_pipe_cfg_set(pipe,  0x000F | DBLB, epnum | dblb);
 515}
 516
 517/*
 518 *              pipe control
 519 */
 520int usbhs_pipe_get_maxpacket(struct usbhs_pipe *pipe)
 521{
 522        /*
 523         * see
 524         *      usbhs_pipe_config_update()
 525         *      usbhs_dcp_malloc()
 526         */
 527        return pipe->maxp;
 528}
 529
 530int usbhs_pipe_is_dir_in(struct usbhs_pipe *pipe)
 531{
 532        return usbhsp_flags_has(pipe, IS_DIR_IN);
 533}
 534
 535int usbhs_pipe_is_dir_host(struct usbhs_pipe *pipe)
 536{
 537        return usbhsp_flags_has(pipe, IS_DIR_HOST);
 538}
 539
 540int usbhs_pipe_is_running(struct usbhs_pipe *pipe)
 541{
 542        return usbhsp_flags_has(pipe, IS_RUNNING);
 543}
 544
 545void usbhs_pipe_running(struct usbhs_pipe *pipe, int running)
 546{
 547        if (running)
 548                usbhsp_flags_set(pipe, IS_RUNNING);
 549        else
 550                usbhsp_flags_clr(pipe, IS_RUNNING);
 551}
 552
 553void usbhs_pipe_data_sequence(struct usbhs_pipe *pipe, int sequence)
 554{
 555        u16 mask = (SQCLR | SQSET);
 556        u16 val;
 557
 558        /*
 559         * sequence
 560         *  0  : data0
 561         *  1  : data1
 562         *  -1 : no change
 563         */
 564        switch (sequence) {
 565        case 0:
 566                val = SQCLR;
 567                break;
 568        case 1:
 569                val = SQSET;
 570                break;
 571        default:
 572                return;
 573        }
 574
 575        usbhsp_pipectrl_set(pipe, mask, val);
 576}
 577
 578static int usbhs_pipe_get_data_sequence(struct usbhs_pipe *pipe)
 579{
 580        return !!(usbhsp_pipectrl_get(pipe) & SQMON);
 581}
 582
 583void usbhs_pipe_clear(struct usbhs_pipe *pipe)
 584{
 585        if (usbhs_pipe_is_dcp(pipe)) {
 586                usbhs_fifo_clear_dcp(pipe);
 587        } else {
 588                usbhsp_pipectrl_set(pipe, ACLRM, ACLRM);
 589                usbhsp_pipectrl_set(pipe, ACLRM, 0);
 590        }
 591}
 592
 593/* Should call usbhsp_pipe_select() before */
 594void usbhs_pipe_clear_without_sequence(struct usbhs_pipe *pipe,
 595                                       int needs_bfre, int bfre_enable)
 596{
 597        int sequence;
 598
 599        usbhsp_pipe_select(pipe);
 600        sequence = usbhs_pipe_get_data_sequence(pipe);
 601        if (needs_bfre)
 602                usbhsp_pipe_cfg_set(pipe, BFRE, bfre_enable ? BFRE : 0);
 603        usbhs_pipe_clear(pipe);
 604        usbhs_pipe_data_sequence(pipe, sequence);
 605}
 606
 607void usbhs_pipe_config_change_bfre(struct usbhs_pipe *pipe, int enable)
 608{
 609        if (usbhs_pipe_is_dcp(pipe))
 610                return;
 611
 612        usbhsp_pipe_select(pipe);
 613        /* check if the driver needs to change the BFRE value */
 614        if (!(enable ^ !!(usbhsp_pipe_cfg_get(pipe) & BFRE)))
 615                return;
 616
 617        usbhs_pipe_clear_without_sequence(pipe, 1, enable);
 618}
 619
 620static struct usbhs_pipe *usbhsp_get_pipe(struct usbhs_priv *priv, u32 type)
 621{
 622        struct usbhs_pipe *pos, *pipe;
 623        int i;
 624
 625        /*
 626         * find target pipe
 627         */
 628        pipe = NULL;
 629        usbhs_for_each_pipe_with_dcp(pos, priv, i) {
 630                if (!usbhs_pipe_type_is(pos, type))
 631                        continue;
 632                if (usbhsp_flags_has(pos, IS_USED))
 633                        continue;
 634
 635                pipe = pos;
 636                break;
 637        }
 638
 639        if (!pipe)
 640                return NULL;
 641
 642        /*
 643         * initialize pipe flags
 644         */
 645        usbhsp_flags_init(pipe);
 646        usbhsp_flags_set(pipe, IS_USED);
 647
 648        return pipe;
 649}
 650
 651static void usbhsp_put_pipe(struct usbhs_pipe *pipe)
 652{
 653        usbhsp_flags_init(pipe);
 654}
 655
 656void usbhs_pipe_init(struct usbhs_priv *priv,
 657                     int (*dma_map_ctrl)(struct device *dma_dev,
 658                                         struct usbhs_pkt *pkt, int map))
 659{
 660        struct usbhs_pipe_info *info = usbhs_priv_to_pipeinfo(priv);
 661        struct usbhs_pipe *pipe;
 662        int i;
 663
 664        usbhs_for_each_pipe_with_dcp(pipe, priv, i) {
 665                usbhsp_flags_init(pipe);
 666                pipe->fifo = NULL;
 667                pipe->mod_private = NULL;
 668                INIT_LIST_HEAD(&pipe->list);
 669
 670                /* pipe force init */
 671                usbhs_pipe_clear(pipe);
 672        }
 673
 674        info->dma_map_ctrl = dma_map_ctrl;
 675}
 676
 677struct usbhs_pipe *usbhs_pipe_malloc(struct usbhs_priv *priv,
 678                                     int endpoint_type,
 679                                     int dir_in)
 680{
 681        struct device *dev = usbhs_priv_to_dev(priv);
 682        struct usbhs_pipe *pipe;
 683        int is_host = usbhs_mod_is_host(priv);
 684        int ret;
 685        u16 pipecfg, pipebuf;
 686
 687        pipe = usbhsp_get_pipe(priv, endpoint_type);
 688        if (!pipe) {
 689                dev_err(dev, "can't get pipe (%s)\n",
 690                        usbhsp_pipe_name[endpoint_type]);
 691                return NULL;
 692        }
 693
 694        INIT_LIST_HEAD(&pipe->list);
 695
 696        usbhs_pipe_disable(pipe);
 697
 698        /* make sure pipe is not busy */
 699        ret = usbhsp_pipe_barrier(pipe);
 700        if (ret < 0) {
 701                dev_err(dev, "pipe setup failed %d\n", usbhs_pipe_number(pipe));
 702                return NULL;
 703        }
 704
 705        if (usbhsp_setup_pipecfg(pipe, is_host, dir_in, &pipecfg)) {
 706                dev_err(dev, "can't setup pipe\n");
 707                return NULL;
 708        }
 709
 710        pipebuf  = usbhsp_setup_pipebuff(pipe);
 711
 712        usbhsp_pipe_select(pipe);
 713        usbhsp_pipe_cfg_set(pipe, 0xFFFF, pipecfg);
 714        usbhsp_pipe_buf_set(pipe, 0xFFFF, pipebuf);
 715        usbhs_pipe_clear(pipe);
 716
 717        usbhs_pipe_sequence_data0(pipe);
 718
 719        dev_dbg(dev, "enable pipe %d : %s (%s)\n",
 720                usbhs_pipe_number(pipe),
 721                usbhs_pipe_name(pipe),
 722                usbhs_pipe_is_dir_in(pipe) ? "in" : "out");
 723
 724        /*
 725         * epnum / maxp are still not set to this pipe.
 726         * call usbhs_pipe_config_update() after this function !!
 727         */
 728
 729        return pipe;
 730}
 731
 732void usbhs_pipe_free(struct usbhs_pipe *pipe)
 733{
 734        usbhsp_put_pipe(pipe);
 735}
 736
 737void usbhs_pipe_select_fifo(struct usbhs_pipe *pipe, struct usbhs_fifo *fifo)
 738{
 739        if (pipe->fifo)
 740                pipe->fifo->pipe = NULL;
 741
 742        pipe->fifo = fifo;
 743
 744        if (fifo)
 745                fifo->pipe = pipe;
 746}
 747
 748
 749/*
 750 *              dcp control
 751 */
 752struct usbhs_pipe *usbhs_dcp_malloc(struct usbhs_priv *priv)
 753{
 754        struct usbhs_pipe *pipe;
 755
 756        pipe = usbhsp_get_pipe(priv, USB_ENDPOINT_XFER_CONTROL);
 757        if (!pipe)
 758                return NULL;
 759
 760        INIT_LIST_HEAD(&pipe->list);
 761
 762        /*
 763         * call usbhs_pipe_config_update() after this function !!
 764         */
 765
 766        return pipe;
 767}
 768
 769void usbhs_dcp_control_transfer_done(struct usbhs_pipe *pipe)
 770{
 771        struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe);
 772
 773        WARN_ON(!usbhs_pipe_is_dcp(pipe));
 774
 775        usbhs_pipe_enable(pipe);
 776
 777        if (!usbhs_mod_is_host(priv)) /* funconly */
 778                usbhsp_pipectrl_set(pipe, CCPL, CCPL);
 779}
 780
 781void usbhs_dcp_dir_for_host(struct usbhs_pipe *pipe, int dir_out)
 782{
 783        usbhsp_pipe_cfg_set(pipe, DIR_OUT,
 784                            dir_out ? DIR_OUT : 0);
 785}
 786
 787/*
 788 *              pipe module function
 789 */
 790int usbhs_pipe_probe(struct usbhs_priv *priv)
 791{
 792        struct usbhs_pipe_info *info = usbhs_priv_to_pipeinfo(priv);
 793        struct usbhs_pipe *pipe;
 794        struct device *dev = usbhs_priv_to_dev(priv);
 795        struct renesas_usbhs_driver_pipe_config *pipe_configs =
 796                                        usbhs_get_dparam(priv, pipe_configs);
 797        int pipe_size = usbhs_get_dparam(priv, pipe_size);
 798        int i;
 799
 800        /* This driver expects 1st pipe is DCP */
 801        if (pipe_configs[0].type != USB_ENDPOINT_XFER_CONTROL) {
 802                dev_err(dev, "1st PIPE is not DCP\n");
 803                return -EINVAL;
 804        }
 805
 806        info->pipe = kcalloc(pipe_size, sizeof(struct usbhs_pipe),
 807                             GFP_KERNEL);
 808        if (!info->pipe)
 809                return -ENOMEM;
 810
 811        info->size = pipe_size;
 812
 813        /*
 814         * init pipe
 815         */
 816        usbhs_for_each_pipe_with_dcp(pipe, priv, i) {
 817                pipe->priv = priv;
 818
 819                usbhs_pipe_type(pipe) =
 820                        pipe_configs[i].type & USB_ENDPOINT_XFERTYPE_MASK;
 821
 822                dev_dbg(dev, "pipe %x\t: %s\n",
 823                        i, usbhsp_pipe_name[pipe_configs[i].type]);
 824        }
 825
 826        return 0;
 827}
 828
 829void usbhs_pipe_remove(struct usbhs_priv *priv)
 830{
 831        struct usbhs_pipe_info *info = usbhs_priv_to_pipeinfo(priv);
 832
 833        kfree(info->pipe);
 834}
 835