Skip to main content

xc2bit/
fusemap_physical.rs

1/*
2Copyright (c) 2016-2017, Robert Ou <rqou@robertou.com> and contributors
3All rights reserved.
4
5Redistribution and use in source and binary forms, with or without
6modification, are permitted provided that the following conditions are met:
7
81. Redistributions of source code must retain the above copyright notice,
9   this list of conditions and the following disclaimer.
102. Redistributions in binary form must reproduce the above copyright notice,
11   this list of conditions and the following disclaimer in the documentation
12   and/or other materials provided with the distribution.
13
14THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
15ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
18FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
21CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
22OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24*/
25
26use crate::*;
27
28pub fn fuse_array_dims(device: XC2Device) -> (usize, usize) {
29    match device {
30        XC2Device::XC2C32 | XC2Device::XC2C32A => (260, 50),
31        XC2Device::XC2C64 | XC2Device::XC2C64A => (274, 98),
32        XC2Device::XC2C128 => (752, 82),
33        XC2Device::XC2C256 => (1364, 98),
34        XC2Device::XC2C384 => (1868, 122),
35        XC2Device::XC2C512 => (1980, 162),
36    }
37}
38
39pub fn and_block_loc(device: XC2Device, fb: u32) -> (usize, usize, bool) {
40    match device {
41        // "Type 1" blocks (OR array is in the middle)
42        XC2Device::XC2C32 | XC2Device::XC2C32A => {
43            match fb {
44                // left
45                0 => (10, 0, false),
46                // right
47                1 => (249, 0, true),
48                _ => unreachable!(),
49            }
50        },
51        XC2Device::XC2C64 | XC2Device::XC2C64A => {
52            match fb {
53                0 => (9, 0, false),                 1 => (264, 0, true),
54                2 => (9, 48, false),                3 => (264, 48, true),
55                _ => unreachable!(),
56            }
57        },
58        XC2Device::XC2C256 => {
59            match fb {
60                // group 0
61                0 => (11, 0 , false),               1 => (330, 0 , true),
62                2 => (11, 48 , false),              3 => (330, 48 , true),
63                // group 1
64                4 => (351, 0 , false),              5 => (670, 0 , true),
65                6 => (351, 48 , false),             7 => (670, 48, true),
66                // group 2
67                8 => (693, 0 , false),              9 => (1012, 0 , true),
68                10 => (693, 48 , false),            11 => (1012, 48 , true),
69                // group 3
70                12 => (1033, 0 , false),            13 => (1352, 0 , true),
71                14 => (1033, 48 , false),           15 => (1352, 48 , true),
72                _ => unreachable!(),
73            }
74        },
75        // "Type 2" blocks (OR array is on the sides)
76        XC2Device::XC2C128 => {
77            match fb {
78                // group 0
79                0 => (48, 0, false),                1 => (327, 0, true),
80                2 => (48, 40, false),               3 => (327, 40, true),
81                // group 1
82                4 => (424, 0, false),               5 => (703, 0, true),
83                6 => (424, 40, false),              7 => (703, 40, true),
84                _ => unreachable!(),
85            }
86        },
87        XC2Device::XC2C384 => {
88            match fb {
89                // group 0
90                0 => (48, 0, false),                1 => (419, 0, true),
91                2 => (48, 40, false),               3 => (419, 40, true),
92                4 => (48, 80, false),               5 => (419, 80, true),
93                // group 1
94                6 => (514, 0, false),               7 => (885, 0, true),
95                8 => (514, 40, false),              9 => (885, 40, true),
96                10 => (514, 80, false),             11 => (885, 80, true),
97                // group 2
98                12 => (982, 0, false),              13 => (1353, 0, true),
99                14 => (982, 40, false),             15 => (1353, 40, true),
100                16 => (982, 80, false),             17 => (1353, 80, true),
101                // group 3
102                18 => (1448, 0, false),             19 => (1819, 0, true),
103                20 => (1448, 40, false),            21 => (1819, 40, true),
104                22 => (1448, 80, false),            23 => (1819, 80, true),
105                _ => unreachable!(),
106            }
107        },
108        XC2Device::XC2C512 => {
109            match fb {
110                // group 0
111                0 => (48, 0, false),                1 => (447, 0, true),
112                2 => (48, 40, false),               3 => (447, 40, true),
113                4 => (48, 80, false),               5 => (447, 80, true),
114                6 => (48, 120, false),              7 => (447, 120, true),
115                // group 1
116                8 => (542, 0, false),               9 => (941, 0, true),
117                10 => (542, 40, false),             11 => (941, 40, true),
118                12 => (542, 80, false),             13 => (941, 80, true),
119                14 => (542, 120, false),            15 => (941, 120, true),
120                // group 2
121                16 => (1038, 0, false),             17 => (1437, 0, true),
122                18 => (1038, 40, false),            19 => (1437, 40, true),
123                20 => (1038, 80, false),            21 => (1437, 80, true),
124                22 => (1038, 120, false),           23 => (1437, 120, true),
125                // group 3
126                24 => (1532, 0, false),             25 => (1931, 0, true),
127                26 => (1532, 40, false),            27 => (1931, 40, true),
128                28 => (1532, 80, false),            29 => (1931, 80, true),
129                30 => (1532, 120, false),           31 => (1931, 120, true),
130                _ => unreachable!(),
131            }
132        },
133    }
134}
135
136pub fn or_block_loc(device: XC2Device, fb: u32) -> (usize, usize, bool) {
137    match device {
138        // "Type 1" blocks (OR array is in the middle)
139        XC2Device::XC2C32 | XC2Device::XC2C32A | XC2Device::XC2C64 | XC2Device::XC2C64A | XC2Device::XC2C256 => {
140            // We know we are in the middle of the AND array
141            let (and_x, and_y, mirror) = and_block_loc(device, fb);
142            (and_x, and_y + 20, mirror)
143        },
144        // "Type 2" blocks (OR array is on the sides)
145        XC2Device::XC2C128 | XC2Device::XC2C384 | XC2Device::XC2C512 => {
146            // "left-hand" non-mirrored blocks need to shift left 32
147            // "right-hand" mirrored blocks need to shift right 32
148            let (and_x, and_y, mirror) = and_block_loc(device, fb);
149            if !mirror {
150                (and_x - 32, and_y, mirror)
151            } else {
152                (and_x + 32, and_y, mirror)
153            }
154        },
155    }
156}
157
158pub fn zia_block_loc(device: XC2Device, fb: u32) -> (usize, usize) {
159    // The ZIA is always to the right of the "left-hand" even-numbered FB. If the FB is odd-numbered, it shifts
160    // right by 1.
161
162    let (and_x, and_y, _) = and_block_loc(device, (fb / 2) * 2);
163
164    if fb % 2 == 0 {
165        // "left-hand"
166        (and_x + 112, and_y)
167    } else {
168        // "right-hand"
169        (and_x + 113, and_y)
170    }
171}
172
173pub fn mc_block_loc(device: XC2Device, fb: u32) -> (usize, usize, bool) {
174    match device {
175        // "OR in the middle" but "small" macrocells (note that internal bit ordering is different!)
176        XC2Device::XC2C32 | XC2Device::XC2C32A | XC2Device::XC2C64 | XC2Device::XC2C64A => {
177            let (and_x, and_y, mirror) = and_block_loc(device, fb);
178            if !mirror {
179                (and_x - 9, and_y, mirror)
180            } else {
181                (and_x + 9, and_y, mirror)
182            }
183        },
184        // "OR in the middle" but "large" macrocells
185        XC2Device::XC2C256 => {
186            let (and_x, and_y, mirror) = and_block_loc(device, fb);
187            if !mirror {
188                (and_x - 10, and_y, mirror)
189            } else {
190                (and_x + 10, and_y, mirror)
191            }
192        },
193        // "OR on the side" (can only be with "large" macrocells, but these are different from the 256 ones)
194        XC2Device::XC2C128 | XC2Device::XC2C384 | XC2Device::XC2C512 => {
195            let (or_x, or_y, mirror) = or_block_loc(device, fb);
196            if !mirror {
197                (or_x - 15, or_y, mirror)
198            } else {
199                (or_x + 15, or_y, mirror)
200            }
201        }
202    }
203}
204
205pub fn gck_fuse_coords(device: XC2Device) -> ((usize, usize), (usize, usize), (usize, usize)) {
206    match device {
207        XC2Device::XC2C32 | XC2Device::XC2C32A => ((126, 23), (127, 23), (128, 23)),
208        XC2Device::XC2C64 | XC2Device::XC2C64A => ((133, 23), (134, 23), (135, 23)),
209        XC2Device::XC2C128 => ((365, 67), (366, 67), (367, 67)),
210        XC2Device::XC2C256 => ((519, 23), (520, 23), (521, 23)),
211        XC2Device::XC2C384 => ((467, 102), (468, 102), (469, 102)),
212        XC2Device::XC2C512 => ((979, 147), (980, 147), (981, 147)),
213    }
214}
215
216// (enable, invert)
217pub fn gsr_fuse_coords(device: XC2Device) -> ((usize, usize), (usize, usize)) {
218    match device {
219        XC2Device::XC2C32 | XC2Device::XC2C32A => ((130, 23), (129, 23)),
220        XC2Device::XC2C64 | XC2Device::XC2C64A => ((136, 73), (135, 73)),
221        XC2Device::XC2C128 => ((2, 67), (1, 67)),
222        XC2Device::XC2C256 => ((179, 23), (178, 23)),
223        XC2Device::XC2C384 => ((2, 97), (1, 97)),
224        XC2Device::XC2C512 => ((2, 27), (1, 27)),
225    }
226}
227
228// (enable, invert)
229pub fn gts_fuse_coords(device: XC2Device) ->
230    (((usize, usize), (usize, usize)), ((usize, usize), (usize, usize)),
231     ((usize, usize), (usize, usize)), ((usize, usize), (usize, usize))) {
232
233    match device {
234        XC2Device::XC2C32 | XC2Device::XC2C32A =>
235            (((127, 24), (126, 24)), ((129, 24), (128, 24)), ((127, 25), (126, 25)), ((129, 25), (128, 25))),
236        XC2Device::XC2C64 | XC2Device::XC2C64A =>
237            (((134, 24), (133, 24)), ((136, 24), (135, 24)), ((138, 73), (137, 73)), ((138, 24), (137, 24))),
238        XC2Device::XC2C128 =>
239            (((5, 27), (4, 27)), ((7, 27), (6, 27)), ((5, 67), (4, 67)), ((7, 67), (6, 67))),
240        XC2Device::XC2C256 =>
241            (((182, 23), (181, 23)), ((177, 24), (176, 24)), ((179, 24), (178, 24)), ((182, 24), (181, 24))),
242        XC2Device::XC2C384 =>
243            (((463, 107), (463, 102)), ((464, 107), (464, 102)), ((465, 107), (465, 102)), ((466, 107), (466, 102))),
244        XC2Device::XC2C512 =>
245            (((4, 27), (3, 27)), ((481, 27), (480, 27)), ((6, 27), (5, 27)), ((8, 27), (7, 27))),
246    }
247}
248
249pub fn global_term_fuse_coord(device: XC2Device) -> (usize, usize) {
250    match device {
251        XC2Device::XC2C32 | XC2Device::XC2C32A => (131, 23),
252        XC2Device::XC2C64 | XC2Device::XC2C64A => (136, 23),
253        XC2Device::XC2C128 => (370, 67),
254        XC2Device::XC2C256 => (517, 23),
255        XC2Device::XC2C384 => (931, 17),
256        XC2Device::XC2C512 => (983, 147),
257    }
258}
259
260// enable, div, div, div, delay
261pub fn clock_div_fuse_coord(device: XC2Device)
262    -> ((usize, usize), (usize, usize), (usize, usize), (usize, usize), (usize, usize)) {
263
264    match device {
265        XC2Device::XC2C32 | XC2Device::XC2C32A | XC2Device::XC2C64 | XC2Device::XC2C64A => unreachable!(),
266        XC2Device::XC2C128 => ((364, 67), (363, 67), (362, 67), (361, 67), (360, 67)),
267        XC2Device::XC2C256 => ((519, 24), (518, 24), (517, 24), (516, 24), (515, 24)),
268        XC2Device::XC2C384 => ((471, 107), (470, 107), (469, 107), (468, 107), (467, 107)),
269        XC2Device::XC2C512 => ((978, 147), (977, 147), (976, 147), (975, 147), (974, 147)),
270    }
271}