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
155
156
157
158
159
160
|
/*
* Copyright : (C) 2022 Phytium Information Technology, Inc.
* All Rights Reserved.
*
* This program is OPEN SOURCE software: you can redistribute it and/or modify it
* under the terms of the Phytium Public License as published by the Phytium Technology Co.,Ltd,
* either version 1.0 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the Phytium Public License for more details.
*
*
* FilePath: fxmac_bdring.h
* Date: 2022-04-06 14:46:52
* LastEditTime: 2022-04-06 14:46:58
* Description: This file is for
*
* Modify History:
* Ver Who Date Changes
* ----- ------ -------- --------------------------------------
*/
#ifndef DRIVERS_ETH_F_XMAC_BDRING_H
#define DRIVERS_ETH_F_XMAC_BDRING_H
#ifdef __cplusplus
extern "C"
{
#endif
#include "fxmac_bd.h"
#include "ftypes.h"
/**************************** Type Definitions *******************************/
/** This is an internal structure used to maintain the DMA list */
typedef struct
{
uintptr phys_base_addr; /* Physical address of 1st BD in list */
uintptr base_bd_addr; /* Virtual address of 1st BD in list */
uintptr high_bd_addr; /* Virtual address of last BD in the list */
u32 length; /* Total size of ring in bytes */
u32 run_state; /* Flag to indicate DMA is started */
u32 separation; /* Number of bytes between the starting address
of adjacent BDs */
FXmacBd *free_head;
/* First BD in the free group */
FXmacBd *pre_head; /* First BD in the pre-work group */
FXmacBd *hw_head; /* First BD in the work group */
FXmacBd *hw_tail; /* Last BD in the work group */
FXmacBd *post_head;
/* First BD in the post-work group */
FXmacBd *bda_restart;
/* BDA to load when channel is started */
volatile u32 hw_cnt; /* Number of BDs in work group */
u32 pre_cnt; /* Number of BDs in pre-work group */
u32 free_cnt; /* Number of allocatable BDs in the free group */
u32 post_cnt; /* Number of BDs in post-work group */
u32 all_cnt; /* Total Number of BDs for channel */
} FXmacBdRing;
/**
* @name: FXMAC_BD_RING_NEXT
* @msg: Return the next BD from bd_ptr in a list.
*
* @param ring_ptr is the DMA channel to operate on.
* @param bd_ptr is the BD to operate on.
* @return The next BD in the list relative to the bd_ptr parameter.
*/
#define FXMAC_BD_RING_NEXT(ring_ptr, bd_ptr) \
(((uintptr)((void *)(bd_ptr)) >= (ring_ptr)->high_bd_addr) ? (FXmacBd *)((void *)(ring_ptr)->base_bd_addr) : (FXmacBd *)((uintptr)((void *)(bd_ptr)) + (ring_ptr)->separation))
/**
* @name: FXMAC_BD_RING_CNT_CALC
* @msg: Use this macro at initialization time to determine how many BDs will fit
* in a BD list within the given memory constraints.
*
* @param alignment specifies what byte alignment the BDs must fall on and
* must be a power of 2 to get an accurate calculation (32, 64, 128,...)
* @param Bytes is the number of bytes to be used to store BDs.
* @return Number of BDs that can fit in the given memory area
*/
#define FXMAC_BD_RING_CNT_CALC(alignment, Bytes) \
(u32)((Bytes) / (sizeof(FXmacBd)))
/**
* @name: FXMAC_BD_RING_MEM_CALC
* @msg: Use this macro at initialization time to determine how many bytes of memory
* is required to contain a given number of BDs at a given alignment.
* @param alignment specifies what byte alignment the BDs must fall on. This
* parameter must be a power of 2 to get an accurate calculation (32, 64,
* 128,...)
* @param num_bd is the number of BDs to calculate memory size requirements for
* @return The number of bytes of memory required to create a BD list with the
* given memory constraints.
*/
#define FXMAC_BD_RING_MEM_CALC(alignment, num_bd) \
(u32)(sizeof(FXmacBd) * (num_bd))
/**
* @name: FXMAC_BD_RING_GET_CNT
* @msg: Return the total number of BDs allocated by this channel with
* FXmacBdRingCreate().
* @param ring_ptr is the DMA channel to operate on.
* @return The total number of BDs allocated for this channel.
*/
#define FXMAC_BD_RING_GET_CNT(ring_ptr) ((ring_ptr)->all_cnt)
/**
* @name: FXMAC_BD_RING_GET_FREE_CNT
* @msg: Return the number of BDs allocatable with FXmacBdRingAlloc() for pre-
* processing.
*
* @param ring_ptr is the DMA channel to operate on.
* @return The number of BDs currently allocatable.
*/
#define FXMAC_BD_RING_GET_FREE_CNT(ring_ptr) ((ring_ptr)->free_cnt)
/**
* @name: FXMAC_BD_RING_PREV
* @msg: Return the previous BD from bd_ptr in the list.
* @param ring_ptr is the DMA channel to operate on.
* @param bd_ptr is the BD to operate on
* @return The previous BD in the list relative to the bd_ptr parameter.
*/
#define FXMAC_BD_RING_PREV(ring_ptr, bd_ptr) \
(((uintptr)(bd_ptr) <= (ring_ptr)->base_bd_addr) ? (FXmacBd *)(ring_ptr)->high_bd_addr : (FXmacBd *)((uintptr)(bd_ptr) - (ring_ptr)->separation))
/************************** Function Prototypes ******************************/
/*
* Scatter gather DMA related functions in FXmacbdring.c
*/
FError FXmacBdRingCreate(FXmacBdRing *ring_ptr, uintptr phys_addr,
uintptr virt_addr, u32 alignment, u32 bd_count);
FError FXmacBdRingClone(FXmacBdRing *ring_ptr, FXmacBd *src_bd_ptr,
u8 direction);
FError FXmacBdRingAlloc(FXmacBdRing *ring_ptr, u32 num_bd,
FXmacBd **bd_set_ptr);
FError FXmacBdRingUnAlloc(FXmacBdRing *ring_ptr, u32 num_bd,
FXmacBd *bd_set_ptr);
FError FXmacBdRingToHw(FXmacBdRing *ring_ptr, u32 num_bd,
FXmacBd *bd_set_ptr);
FError FXmacBdRingFree(FXmacBdRing *ring_ptr, u32 num_bd,
FXmacBd *bd_set_ptr);
u32 FXmacBdRingFromHwTx(FXmacBdRing *ring_ptr, u32 bd_limit,
FXmacBd **bd_set_ptr);
u32 FXmacBdRingFromHwRx(FXmacBdRing *ring_ptr, u32 bd_limit,
FXmacBd **bd_set_ptr);
FError FXmacBdRingCheck(FXmacBdRing *ring_ptr, u8 direction);
void FXmacBdringPtrReset(FXmacBdRing *ring_ptr, void *virt_addrloc);
#ifdef __cplusplus
}
#endif
#endif
|