// The core logic primitive of the Cyclone V/10GX is the Adaptive Logic Module // (ALM). Each ALM is made up of an 8-input, 2-output look-up table, covered // in this file, connected to combinational outputs, a carry chain, and four // D flip-flops (which are covered as MISTRAL_FF in dff_sim.v). // // The ALM is vertically symmetric, so I find it helps to think in terms of // half-ALMs, as that's predominantly the unit that synth_intel_alm uses. // // ALMs are quite flexible, having multiple modes. // // Normal (combinational) mode // --------------------------- // The ALM can implement: // - a single 6-input function (with the other inputs usable for flip-flop access) // - two 5-input functions that share two inputs // - a 5-input and a 4-input function that share one input // - a 5-input and a 3-or-less-input function that share no inputs // - two 4-or-less-input functions that share no inputs // // Normal-mode functions are represented as MISTRAL_ALUTN cells with N inputs. // It would be possible to represent a normal mode function as a single cell - // the vendor cyclone{v,10gx}_lcell_comb cell does exactly that - but I felt // it was more user-friendly to print out the specific function sizes // separately. // // With the exception of MISTRAL_ALUT6, you can think of two normal-mode cells // fitting inside a single ALM. // // Extended (7-input) mode // ----------------------- // The ALM can also fit a 7-input function made of two 5-input functions that // share four inputs, multiplexed by another input. // // Because this can't accept arbitrary 7-input functions, Yosys can't handle // it, so it doesn't have a cell, but I would likely call it MISTRAL_ALUT7(E?) // if it did, and it would take up a full ALM. // // It might be possible to add an extraction pass to examine all ALUT5 cells // that feed into ALUT3 cells to see if they can be combined into an extended // ALM, but I don't think it will be worth it. // // Arithmetic mode // --------------- // In arithmetic mode, each half-ALM uses its carry chain to perform fast addition // of two four-input functions that share three inputs. Oddly, the result of // one of the functions is inverted before being added (you can see this as // the dot on a full-adder input of Figure 1-8 in the Handbook). // // The cell for an arithmetic-mode half-ALM is MISTRAL_ALM_ARITH. One idea // I've had (or rather was suggested by mwk) is that functions that feed into // arithmetic-mode cells could be packed directly into the arithmetic-mode // cell as a function, which reduces the number of ALMs needed. // // Shared arithmetic mode // ---------------------- // Shared arithmetic mode looks a lot like arithmetic mode, but here the // output of every other four-input function goes to the input of the adder // the next bit along. What this means is that adding three bits together can // be done in an ALM, because functions can be used to implement addition that // then feeds into the carry chain. This means that three bits can be added per // ALM, as opposed to two in the arithmetic mode. // // Shared arithmetic mode doesn't currently have a cell, but I intend to add // it as MISTRAL_ALM_SHARED, and have it occupy a full ALM. Because it adds // three bits per cell, it makes addition shorter and use less ALMs, but // I don't know enough to tell whether it's more efficient to use shared // arithmetic mode to shorten the carry chain, or plain arithmetic mode with // the functions packed in. `default_nettype none // Cyclone V LUT output timings (picoseconds): // // CARRY A B C D E F G // COMBOUT - 605 583 510 512 - 97 400 (LUT6) // COMBOUT - 602 583 457 510 302 93 483 (LUT7) // SUMOUT 368 1342 1323 887 927 - 785 - // CARRYOUT 71 1082 1062 866 813 - 1198 - (* abc9_lut=2, lib_whitebox *) module MISTRAL_ALUT6(input A, B, C, D, E, F, output Q); parameter [63:0] LUT = 64'h0000_0000_0000_0000; `ifdef cyclonev specify (A => Q) = 605; (B => Q) = 583; (C => Q) = 510; (D => Q) = 512; (E => Q) = 400; (F => Q) = 97; endspecify `endif `ifdef cyclone10gx specify (A => Q) = 275; (B => Q) = 272; (C => Q) = 175; (D => Q) = 165; (E => Q) = 162; (F => Q) = 53; endspecify `endif assign Q = LUT >> {F, E, D, C, B, A}; endmodule (* abc9_lut=1, lib_whitebox *) module MISTRAL_ALUT5(input A, B, C, D, E, output Q); parameter [31:0] LUT = 32'h0000_0000; `ifdef cyclonev specify (A => Q) = 583; (B => Q) = 510; (C => Q) = 512; (D => Q) = 400; (E => Q) = 97; endspecify `endif `ifdef cyclone10gx specify (A => Q) = 272; (B => Q) = 175; (C => Q) = 165; (D => Q) = 162; (E => Q) = 53; endspecify `endif assign Q = LUT >> {E, D, C, B, A}; endmodule (* abc9_lut=1, lib_whitebox *) module MISTRAL_ALUT4(input A, B, C, D, output Q); parameter [15:0] LUT = 16'h0000; `ifdef cyclonev specify (A => Q) = 510; (B => Q) = 512; (C => Q) = 400; (D => Q) = 97; endspecify `endif `ifdef cyclone10gx specify (A => Q) = 175; (B => Q) = 165; (C => Q) = 162; (D => Q) = 53; endspecify `endif assign Q = LUT >> {D, C, B, A}; endmodule (* abc9_lut=1, lib_whitebox *) module MISTRAL_ALUT3(input A, B, C, output Q); parameter [7:0] LUT = 8'h00; `ifdef cyclonev specify (A => Q) = 510; (B => Q) = 400; (C => Q) = 97; endspecify `endif `ifdef cyclone10gx specify (A => Q) = 165; (B => Q) = 162; (C => Q) = 53; endspecify `endif assign Q = LUT >> {C, B, A}; endmodule (* abc9_lut=1, lib_whitebox *) module MISTRAL_ALUT2(input A, B, output Q); parameter [3:0] LUT = 4'h0; `ifdef cyclonev specify (A => Q) = 400; (B => Q) = 97; endspecify `endif `ifdef cyclone10gx specify (A => Q) = 162; (B => Q) = 53; endspecify `endif assign Q = LUT >> {B, A}; endmodule (* abc9_lut=1, lib_whitebox *) module MISTRAL_NOT(input A, output Q); `ifdef cyclonev specify (A => Q) = 97; endspecify `endif `ifdef cyclone10gx specify (A => Q) = 53; endspecify `endif assign Q = ~A; endmodule // Despite the abc9_carry attributes, this doesn't seem to stop ABC9 adding illegal fanout to the carry chain that nextpnr cannot handle. // So we treat it as a total blackbox from ABC9's perspective for now. // (* abc9_box, lib_whitebox *) module MISTRAL_ALUT_ARITH(input A, B, C, D0, D1, /* (* abc9_carry *) */ input CI, output SO, /* (* abc9_carry *) */ output CO); parameter LUT0 = 16'h0000; parameter LUT1 = 16'h0000; `ifdef cyclonev specify (A => SO) = 1342; (B => SO) = 1323; (C => SO) = 927; (D0 => SO) = 887; (D1 => SO) = 785; (CI => SO) = 368; (A => CO) = 1082; (B => CO) = 1062; (C => CO) = 813; (D0 => CO) = 866; (D1 => CO) = 1198; (CI => CO) = 36; // Divided by 2 to account for there being two ALUT_ARITHs in an ALM) endspecify `endif `ifdef cyclone10gx specify (A => SO) = 644; (B => SO) = 477; (C => SO) = 416; (D0 => SO) = 380; (D1 => SO) = 431; (CI => SO) = 276; (A => CO) = 525; (B => CO) = 433; (C => CO) = 712; (D0 => CO) = 653; (D1 => CO) = 593; (CI => CO) = 16; endspecify `endif wire q0, q1; assign q0 = LUT0 >> {D0, C, B, A}; assign q1 = LUT1 >> {D1, C, B, A}; assign {CO, SO} = q0 + !q1 + CI; endmodule /* // A, B, C0, C1, E0, E1, F0, F1: data inputs // CARRYIN: carry input // SHAREIN: shared-arithmetic input // CLK0, CLK1, CLK2: clock inputs // // COMB0, COMB1: combinational outputs // FF0, FF1, FF2, FF3: DFF outputs // SUM0, SUM1: adder outputs // CARRYOUT: carry output // SHAREOU
/*
ChibiOS - Copyright (C) 2006..2018 Giovanni Di Sirio
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
/**
* @file CW/ccportab.h
* @brief Compiler portability layer.
*
* @defgroup CC_PORTAB Compiler portability.
* @{
*/
#ifndef CCPORTAB_H
#define CCPORTAB_H
/*===========================================================================*/
/* Module constants. */
/*===========================================================================*/
/*===========================================================================*/
/* Module pre-compile time settings. */
/*===========================================================================*/
/*===========================================================================*/
/* Derived constants and error checks. */
/*===========================================================================*/
/*===========================================================================*/
/* Module data structures and types. */
/*===========================================================================*/
/*===========================================================================*/
/* Module macros. */
/*===========================================================================*/
/**
* @name Compiler abstraction macros
* @{
*/
/**
* @brief Allocates a variable or function to a specific section.
* @note If the compiler does not support such a feature then this macro
* must not be defined or it could originate errors.
*/
#define CC_SECTION(s) __declspec (section s)
/**
* @brief Marks a function or variable as a weak symbol.
* @note If the compiler does not support such a feature then this macro
* must not be defined or it could originate errors.
*/
//#define CC_WEAK __attribute__((weak))
/**
* @brief Marks a function or variable as used.
* @details The compiler or linker shall not remove the marked function or
* variable regardless if it is referred or not in the code.
* @note If the compiler does not support such a feature then this macro
* must not be defined or it could originate errors.
*/
#define CC_USED __attribute__((used))
/**
* @brief Enforces alignment of the variable or function declared afterward.
* @note If the compiler does not support such a feature then this macro
* must not be defined or it could originate errors.
*/
//#define CC_ALIGN(n) __attribute__((aligned(n)))
/**
* @brief Enforces packing of the structure declared afterward.
* @note If the compiler does not support such a feature then this macro
* must not be defined or it could originate errors.
*/
//#define CC_PACK __attribute__((packed))
/**
* @brief Marks a function as not inlineable.
* @note Can be implemented as an empty macro if not supported by the
* compiler.
*/
#define CC_NO_INLINE __declspec(never_inline)
/**
* @brief Enforces a function inline.
* @note Can be implemented as an empty macro if not supported by the
* compiler.
*/
#define CC_FORCE_INLINE //__attribute__((always_inline))
/**
* @brief Marks a function as non-returning.
* @note Can be implemented as an empty macro if not supported by the
* compiler.
*/
#define CC_NO_RETURN //__attribute__((noreturn))
/** @} */
/*===========================================================================*/
/* External declarations. */
/*===========================================================================*/
#ifdef __cplusplus
extern "C" {
#endif
#ifdef __cplusplus
}
#endif
/*===========================================================================*/
/* Module inline functions. */
/*===========================================================================*/
#endif /* CCPORTAB_H */
/** @} */