aboutsummaryrefslogtreecommitdiff
path: root/hw/net/fsl_etsec/etsec.h
blob: 3860864a3f5f6a35e4a70872eed7f1f0b574ed5e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
/*
 * QEMU Freescale eTSEC Emulator
 *
 * Copyright (c) 2011-2013 AdaCore
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */

#ifndef ETSEC_H
#define ETSEC_H

#include "hw/sysbus.h"
#include "net/net.h"
#include "hw/ptimer.h"
#include "qom/object.h"

/* Buffer Descriptors */

typedef struct eTSEC_rxtx_bd {
    uint16_t flags;
    uint16_t length;
    uint32_t bufptr;
} eTSEC_rxtx_bd;

#define BD_WRAP       (1 << 13)
#define BD_INTERRUPT  (1 << 12)
#define BD_LAST       (1 << 11)

#define BD_TX_READY     (1 << 15)
#define BD_TX_PADCRC    (1 << 14)
#define BD_TX_TC        (1 << 10)
#define BD_TX_PREDEF    (1 << 9)
#define BD_TX_HFELC     (1 << 7)
#define BD_TX_CFRL      (1 << 6)
#define BD_TX_RC_MASK   0xF
#define BD_TX_RC_OFFSET 0x2
#define BD_TX_TOEUN     (1 << 1)
#define BD_TX_TR        (1 << 0)

#define BD_RX_EMPTY     (1 << 15)
#define BD_RX_RO1       (1 << 14)
#define BD_RX_FIRST     (1 << 10)
#define BD_RX_MISS      (1 << 8)
#define BD_RX_BROADCAST (1 << 7)
#define BD_RX_MULTICAST (1 << 6)
#define BD_RX_LG        (1 << 5)
#define BD_RX_NO        (1 << 4)
#define BD_RX_SH        (1 << 3)
#define BD_RX_CR        (1 << 2)
#define BD_RX_OV        (1 << 1)
#define BD_RX_TR        (1 << 0)

/* Tx FCB flags */
#define FCB_TX_VLN     (1 << 7)
#define FCB_TX_IP      (1 << 6)
#define FCB_TX_IP6     (1 << 5)
#define FCB_TX_TUP     (1 << 4)
#define FCB_TX_UDP     (1 << 3)
#define FCB_TX_CIP     (1 << 2)
#define FCB_TX_CTU     (1 << 1)
#define FCB_TX_NPH     (1 << 0)

/* eTSEC */

/* Number of register in the device */
#define ETSEC_REG_NUMBER 1024

typedef struct eTSEC_Register {
    const char *name;
    const char *desc;
    uint32_t    access;
    uint32_t    value;
} eTSEC_Register;

struct eTSEC {
    SysBusDevice  busdev;

    MemoryRegion  io_area;

    eTSEC_Register regs[ETSEC_REG_NUMBER];

    NICState *nic;
    NICConf   conf;

    /* Tx */

    uint8_t       *tx_buffer;
    uint32_t       tx_buffer_len;
    eTSEC_rxtx_bd  first_bd;

    /* Rx */

    uint8_t       *rx_buffer;
    uint32_t       rx_buffer_len;
    uint32_t       rx_remaining_data;
    uint8_t        rx_first_in_frame;
    uint8_t        rx_fcb_size;
    eTSEC_rxtx_bd  rx_first_bd;
    uint8_t        rx_fcb[10];
    uint32_t       rx_padding;

    /* IRQs */
    qemu_irq     tx_irq;
    qemu_irq     rx_irq;
    qemu_irq     err_irq;


    uint16_t phy_status;
    uint16_t phy_control;

    /* Polling */
    struct ptimer_state *ptimer;

    /* Whether we should flush the rx queue when buffer becomes available. */
    bool need_flush;
};
typedef struct eTSEC eTSEC;

#define TYPE_ETSEC_COMMON "eTSEC"
OBJECT_DECLARE_SIMPLE_TYPE(eTSEC, ETSEC_COMMON)

#define eTSEC_TRANSMIT 1
#define eTSEC_RECEIVE  2

void etsec_update_irq(eTSEC *etsec);

void etsec_walk_tx_ring(eTSEC *etsec, int ring_nbr);
void etsec_walk_rx_ring(eTSEC *etsec, int ring_nbr);
ssize_t etsec_rx_ring_write(eTSEC *etsec, const uint8_t *buf, size_t size);

void etsec_write_miim(eTSEC          *etsec,
                      eTSEC_Register *reg,
                      uint32_t        reg_index,
                      uint32_t        value);

void etsec_miim_link_status(eTSEC *etsec, NetClientState *nc);

#endif /* ETSEC_H */