Skip to content

Commit 31d97c2

Browse files
committedJun 12, 2017
xc2bit: Fix bug with 32A ZIA encoding
The much earlier fix for the larger macrocell devices was causing the 32-macrocell ZIA bits to get mirrored. Also, for the sake of consistency, replace the 32-macrocell ZIA encode/decode with a pattern match rather than explicitly setting mux bits
1 parent 03e0c4b commit 31d97c2

File tree

1 file changed

+49
-55
lines changed

1 file changed

+49
-55
lines changed
 

Diff for: ‎src/xc2bit/src/zia.rs

+49-55
Original file line numberDiff line numberDiff line change
@@ -9154,80 +9154,74 @@ pub static ZIA_MAP_512: [[XC2ZIAInput; 78]; INPUTS_PER_ANDTERM] = [
91549154
XC2ZIAInput::IBuf{ibuf: 0}],
91559155
];
91569156

9157+
const T: bool = true;
9158+
const F: bool = false;
9159+
91579160
/// Internal function that reads a piece of the ZIA corresponding to one FB and one row
91589161
pub fn read_32_zia_fb_row_logical(fuses: &[bool], block_idx: usize, row_idx: usize)
91599162
-> Result<XC2ZIARowPiece, &'static str> {
91609163

9161-
let mut zia_row_fuses = [false; 8];
9162-
9163-
for i in 0..8 {
9164-
zia_row_fuses[7 - i] = fuses[block_idx + row_idx * 8 + i];
9165-
}
9166-
9167-
// 7th bit is active-high unlike the rest
9168-
zia_row_fuses[7] = !zia_row_fuses[7];
9169-
9170-
let mut active_bit = 8;
9171-
for i in 0..8 {
9172-
// active low
9173-
if !zia_row_fuses[i] {
9174-
if active_bit != 8 {
9175-
return Err("multiple ZIA inputs selected!");
9176-
}
9177-
9178-
active_bit = i;
9179-
}
9180-
}
9164+
// This is an ugly workaround for the lack of stable slice patterns
9165+
let zia_row_fuses = (
9166+
fuses[block_idx + row_idx * 8 + 0],
9167+
fuses[block_idx + row_idx * 8 + 1],
9168+
fuses[block_idx + row_idx * 8 + 2],
9169+
fuses[block_idx + row_idx * 8 + 3],
9170+
fuses[block_idx + row_idx * 8 + 4],
9171+
fuses[block_idx + row_idx * 8 + 5],
9172+
fuses[block_idx + row_idx * 8 + 6],
9173+
fuses[block_idx + row_idx * 8 + 7],
9174+
);
91819175

9182-
if active_bit == 8 {
9183-
// FIXME: Is this an error?
9184-
return Err("no ZIA inputs selected!");
9185-
}
9176+
let selected_input = match zia_row_fuses {
9177+
(F, T, T, T, T, T, T, F) => ZIA_MAP_32[row_idx][0],
9178+
(F, T, T, T, T, T, F, T) => ZIA_MAP_32[row_idx][1],
9179+
(F, T, T, T, T, F, T, T) => ZIA_MAP_32[row_idx][2],
9180+
(F, T, T, T, F, T, T, T) => ZIA_MAP_32[row_idx][3],
9181+
(F, T, T, F, T, T, T, T) => ZIA_MAP_32[row_idx][4],
9182+
(F, T, F, T, T, T, T, T) => ZIA_MAP_32[row_idx][5],
9183+
(T, T, T, T, T, T, T, T) => XC2ZIAInput::One,
9184+
(F, F, T, T, T, T, T, T) => XC2ZIAInput::Zero,
9185+
_ => return Err("unknown ZIA input choice"),
9186+
};
91869187

91879188
Ok(XC2ZIARowPiece {
9188-
selected: if active_bit == 6 {
9189-
XC2ZIAInput::Zero
9190-
} else if active_bit == 7 {
9191-
XC2ZIAInput::One
9192-
} else {
9193-
ZIA_MAP_32[row_idx][active_bit]
9194-
}
9189+
selected: selected_input
91959190
})
91969191
}
91979192

91989193
/// Internal function that takes a ZIA row and choice and returns the bit encoding for it
91999194
pub fn encode_32_zia_choice(row: u32, choice: XC2ZIAInput) -> Option<[bool; 8]> {
92009195
if choice == XC2ZIAInput::One {
9201-
Some([true, true, true, true, true, true, true, true])
9196+
Some([T, T, T, T, T, T, T, T])
92029197
} else if choice == XC2ZIAInput::Zero {
9203-
Some([true, true, true, true, true, true, false, false])
9198+
Some([F, F, T, T, T, T, T, T])
92049199
} else {
9205-
let mut ret = [true; 8];
9206-
// This bit is active-high unlike the rest
9207-
ret[7] = false;
9208-
9209-
let mut found_bit = 8;
9200+
let mut found_bit = ZIA_MAP_32[0].len();
92109201
for i in 0..ZIA_MAP_32[row as usize].len() {
92119202
if choice == ZIA_MAP_32[row as usize][i] {
92129203
found_bit = i;
92139204
break;
92149205
}
92159206
}
92169207

9217-
if found_bit == 8 {
9208+
if found_bit == ZIA_MAP_32[0].len() {
92189209
// Didn't find it
92199210
return None;
92209211
}
92219212

9222-
ret[found_bit] = false;
9223-
9224-
Some(ret)
9213+
match found_bit {
9214+
0 => Some([F, T, T, T, T, T, T, F]),
9215+
1 => Some([F, T, T, T, T, T, F, T]),
9216+
2 => Some([F, T, T, T, T, F, T, T]),
9217+
3 => Some([F, T, T, T, F, T, T, T]),
9218+
4 => Some([F, T, T, F, T, T, T, T]),
9219+
5 => Some([F, T, F, T, T, T, T, T]),
9220+
_ => unreachable!(),
9221+
}
92259222
}
92269223
}
92279224

9228-
const T: bool = true;
9229-
const F: bool = false;
9230-
92319225
/// Internal function that reads a piece of the ZIA corresponding to one FB and one row
92329226
pub fn read_64_zia_fb_row_logical(fuses: &[bool], block_idx: usize, row_idx: usize)
92339227
-> Result<XC2ZIARowPiece, &'static str> {
@@ -9284,15 +9278,15 @@ pub fn encode_64_zia_choice(row: u32, choice: XC2ZIAInput) -> Option<[bool; 16]>
92849278
// TODO: This one isn't certain
92859279
Some([T, T, T, T, T, T, T, F, F, T, T, T, T, T, T, T])
92869280
} else {
9287-
let mut found_bit = 12;
9281+
let mut found_bit = ZIA_MAP_64[0].len();
92889282
for i in 0..ZIA_MAP_64[row as usize].len() {
92899283
if choice == ZIA_MAP_64[row as usize][i] {
92909284
found_bit = i;
92919285
break;
92929286
}
92939287
}
92949288

9295-
if found_bit == 12 {
9289+
if found_bit == ZIA_MAP_64[0].len() {
92969290
// Didn't find it
92979291
return None;
92989292
}
@@ -9393,15 +9387,15 @@ pub fn encode_128_zia_choice(row: u32, choice: XC2ZIAInput) -> Option<[bool; 28]
93939387
// TODO: This one isn't certain
93949388
Some([T, T, T, T, T, T, T, T, F, F, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T])
93959389
} else {
9396-
let mut found_bit = 22;
9390+
let mut found_bit = ZIA_MAP_128[0].len();
93979391
for i in 0..ZIA_MAP_128[row as usize].len() {
93989392
if choice == ZIA_MAP_128[row as usize][i] {
93999393
found_bit = i;
94009394
break;
94019395
}
94029396
}
94039397

9404-
if found_bit == 22 {
9398+
if found_bit == ZIA_MAP_128[0].len() {
94059399
// Didn't find it
94069400
return None;
94079401
}
@@ -9550,15 +9544,15 @@ pub fn encode_256_zia_choice(row: u32, choice: XC2ZIAInput) -> Option<[bool; 48]
95509544
// TODO: This one isn't certain
95519545
Some([T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, F, F, T, T, T, T, T, T])
95529546
} else {
9553-
let mut found_bit = 40;
9547+
let mut found_bit = ZIA_MAP_256[0].len();
95549548
for i in 0..ZIA_MAP_256[row as usize].len() {
95559549
if choice == ZIA_MAP_256[row as usize][i] {
95569550
found_bit = i;
95579551
break;
95589552
}
95599553
}
95609554

9561-
if found_bit == 40 {
9555+
if found_bit == ZIA_MAP_256[0].len() {
95629556
// Didn't find it
95639557
return None;
95649558
}
@@ -9773,15 +9767,15 @@ pub fn encode_384_zia_choice(row: u32, choice: XC2ZIAInput) -> Option<[bool; 74]
97739767
// TODO: This one isn't certain
97749768
Some([T, F, F, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T])
97759769
} else {
9776-
let mut found_bit = 62;
9770+
let mut found_bit = ZIA_MAP_384[0].len();
97779771
for i in 0..ZIA_MAP_384[row as usize].len() {
97789772
if choice == ZIA_MAP_384[row as usize][i] {
97799773
found_bit = i;
97809774
break;
97819775
}
97829776
}
97839777

9784-
if found_bit == 62 {
9778+
if found_bit == ZIA_MAP_384[0].len() {
97859779
// Didn't find it
97869780
return None;
97879781
}
@@ -10048,15 +10042,15 @@ pub fn encode_512_zia_choice(row: u32, choice: XC2ZIAInput) -> Option<[bool; 88]
1004810042
// TODO: This one isn't certain
1004910043
Some([T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, F, F, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T])
1005010044
} else {
10051-
let mut found_bit = 78;
10045+
let mut found_bit = ZIA_MAP_512[0].len();
1005210046
for i in 0..ZIA_MAP_512[row as usize].len() {
1005310047
if choice == ZIA_MAP_512[row as usize][i] {
1005410048
found_bit = i;
1005510049
break;
1005610050
}
1005710051
}
1005810052

10059-
if found_bit == 78 {
10053+
if found_bit == ZIA_MAP_512[0].len() {
1006010054
// Didn't find it
1006110055
return None;
1006210056
}

0 commit comments

Comments
 (0)
Please sign in to comment.