mirror of
				https://github.com/YosysHQ/yosys
				synced 2025-10-31 03:32:29 +00:00 
			
		
		
		
	Add new builtin FF types
The new types include: - FFs with async reset and enable (`$adffe`, `$_DFFE_[NP][NP][01][NP]_`) - FFs with sync reset (`$sdff`, `$_SDFF_[NP][NP][01]_`) - FFs with sync reset and enable, reset priority (`$sdffs`, `$_SDFFE_[NP][NP][01][NP]_`) - FFs with sync reset and enable, enable priority (`$sdffce`, `$_SDFFCE_[NP][NP][01][NP]_`) - FFs with async reset, set, and enable (`$dffsre`, `$_DFFSRE_[NP][NP][NP][NP]_`) - latches with reset or set (`$adlatch`, `$_DLATCH_[NP][NP][01]_`) The new FF types are not actually used anywhere yet (this is left for future commits).
This commit is contained in:
		
							parent
							
								
									8c4cb1885b
								
							
						
					
					
						commit
						b0bee396a8
					
				
					 8 changed files with 2736 additions and 70 deletions
				
			
		|  | @ -139,8 +139,14 @@ struct CellTypes | ||||||
| 		setup_type(ID($dff), {ID::CLK, ID::D}, {ID::Q}); | 		setup_type(ID($dff), {ID::CLK, ID::D}, {ID::Q}); | ||||||
| 		setup_type(ID($dffe), {ID::CLK, ID::EN, ID::D}, {ID::Q}); | 		setup_type(ID($dffe), {ID::CLK, ID::EN, ID::D}, {ID::Q}); | ||||||
| 		setup_type(ID($dffsr), {ID::CLK, ID::SET, ID::CLR, ID::D}, {ID::Q}); | 		setup_type(ID($dffsr), {ID::CLK, ID::SET, ID::CLR, ID::D}, {ID::Q}); | ||||||
|  | 		setup_type(ID($dffsre), {ID::CLK, ID::SET, ID::CLR, ID::D, ID::E}, {ID::Q}); | ||||||
| 		setup_type(ID($adff), {ID::CLK, ID::ARST, ID::D}, {ID::Q}); | 		setup_type(ID($adff), {ID::CLK, ID::ARST, ID::D}, {ID::Q}); | ||||||
|  | 		setup_type(ID($adffe), {ID::CLK, ID::ARST, ID::D, ID::E}, {ID::Q}); | ||||||
|  | 		setup_type(ID($sdff), {ID::CLK, ID::SRST, ID::D}, {ID::Q}); | ||||||
|  | 		setup_type(ID($sdffe), {ID::CLK, ID::SRST, ID::D, ID::E}, {ID::Q}); | ||||||
|  | 		setup_type(ID($sdffce), {ID::CLK, ID::SRST, ID::D, ID::E}, {ID::Q}); | ||||||
| 		setup_type(ID($dlatch), {ID::EN, ID::D}, {ID::Q}); | 		setup_type(ID($dlatch), {ID::EN, ID::D}, {ID::Q}); | ||||||
|  | 		setup_type(ID($adlatch), {ID::EN, ID::D, ID::ARST}, {ID::Q}); | ||||||
| 		setup_type(ID($dlatchsr), {ID::EN, ID::SET, ID::CLR, ID::D}, {ID::Q}); | 		setup_type(ID($dlatchsr), {ID::EN, ID::SET, ID::CLR, ID::D}, {ID::Q}); | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
|  | @ -208,14 +214,48 @@ struct CellTypes | ||||||
| 		for (auto c3 : list_01) | 		for (auto c3 : list_01) | ||||||
| 			setup_type(stringf("$_DFF_%c%c%c_", c1, c2, c3), {ID::C, ID::R, ID::D}, {ID::Q}); | 			setup_type(stringf("$_DFF_%c%c%c_", c1, c2, c3), {ID::C, ID::R, ID::D}, {ID::Q}); | ||||||
| 
 | 
 | ||||||
|  | 		for (auto c1 : list_np) | ||||||
|  | 		for (auto c2 : list_np) | ||||||
|  | 		for (auto c3 : list_01) | ||||||
|  | 		for (auto c4 : list_np) | ||||||
|  | 			setup_type(stringf("$_DFFE_%c%c%c%c_", c1, c2, c3, c4), {ID::C, ID::R, ID::D, ID::E}, {ID::Q}); | ||||||
|  | 
 | ||||||
| 		for (auto c1 : list_np) | 		for (auto c1 : list_np) | ||||||
| 		for (auto c2 : list_np) | 		for (auto c2 : list_np) | ||||||
| 		for (auto c3 : list_np) | 		for (auto c3 : list_np) | ||||||
| 			setup_type(stringf("$_DFFSR_%c%c%c_", c1, c2, c3), {ID::C, ID::S, ID::R, ID::D}, {ID::Q}); | 			setup_type(stringf("$_DFFSR_%c%c%c_", c1, c2, c3), {ID::C, ID::S, ID::R, ID::D}, {ID::Q}); | ||||||
| 
 | 
 | ||||||
|  | 		for (auto c1 : list_np) | ||||||
|  | 		for (auto c2 : list_np) | ||||||
|  | 		for (auto c3 : list_np) | ||||||
|  | 		for (auto c4 : list_np) | ||||||
|  | 			setup_type(stringf("$_DFFSRE_%c%c%c%c_", c1, c2, c3, c4), {ID::C, ID::S, ID::R, ID::D, ID::E}, {ID::Q}); | ||||||
|  | 
 | ||||||
|  | 		for (auto c1 : list_np) | ||||||
|  | 		for (auto c2 : list_np) | ||||||
|  | 		for (auto c3 : list_01) | ||||||
|  | 			setup_type(stringf("$_SDFF_%c%c%c_", c1, c2, c3), {ID::C, ID::R, ID::D}, {ID::Q}); | ||||||
|  | 
 | ||||||
|  | 		for (auto c1 : list_np) | ||||||
|  | 		for (auto c2 : list_np) | ||||||
|  | 		for (auto c3 : list_01) | ||||||
|  | 		for (auto c4 : list_np) | ||||||
|  | 			setup_type(stringf("$_SDFFE_%c%c%c%c_", c1, c2, c3, c4), {ID::C, ID::R, ID::D, ID::E}, {ID::Q}); | ||||||
|  | 
 | ||||||
|  | 		for (auto c1 : list_np) | ||||||
|  | 		for (auto c2 : list_np) | ||||||
|  | 		for (auto c3 : list_01) | ||||||
|  | 		for (auto c4 : list_np) | ||||||
|  | 			setup_type(stringf("$_SDFFCE_%c%c%c%c_", c1, c2, c3, c4), {ID::C, ID::R, ID::D, ID::E}, {ID::Q}); | ||||||
|  | 
 | ||||||
| 		for (auto c1 : list_np) | 		for (auto c1 : list_np) | ||||||
| 			setup_type(stringf("$_DLATCH_%c_", c1), {ID::E, ID::D}, {ID::Q}); | 			setup_type(stringf("$_DLATCH_%c_", c1), {ID::E, ID::D}, {ID::Q}); | ||||||
| 
 | 
 | ||||||
|  | 		for (auto c1 : list_np) | ||||||
|  | 		for (auto c2 : list_np) | ||||||
|  | 		for (auto c3 : list_01) | ||||||
|  | 			setup_type(stringf("$_DLATCH_%c%c%c_", c1, c2, c3), {ID::E, ID::R, ID::D}, {ID::Q}); | ||||||
|  | 
 | ||||||
| 		for (auto c1 : list_np) | 		for (auto c1 : list_np) | ||||||
| 		for (auto c2 : list_np) | 		for (auto c2 : list_np) | ||||||
| 		for (auto c3 : list_np) | 		for (auto c3 : list_np) | ||||||
|  |  | ||||||
|  | @ -158,6 +158,9 @@ X(SRC_EN) | ||||||
| X(SRC_PEN) | X(SRC_PEN) | ||||||
| X(SRC_POL) | X(SRC_POL) | ||||||
| X(SRC_WIDTH) | X(SRC_WIDTH) | ||||||
|  | X(SRST) | ||||||
|  | X(SRST_POLARITY) | ||||||
|  | X(SRST_VALUE) | ||||||
| X(STATE_BITS) | X(STATE_BITS) | ||||||
| X(STATE_NUM) | X(STATE_NUM) | ||||||
| X(STATE_NUM_LOG2) | X(STATE_NUM_LOG2) | ||||||
|  |  | ||||||
							
								
								
									
										259
									
								
								kernel/rtlil.cc
									
										
									
									
									
								
							
							
						
						
									
										259
									
								
								kernel/rtlil.cc
									
										
									
									
									
								
							|  | @ -54,8 +54,14 @@ const pool<IdString> &RTLIL::builtin_ff_cell_types() { | ||||||
| 		ID($dff), | 		ID($dff), | ||||||
| 		ID($dffe), | 		ID($dffe), | ||||||
| 		ID($dffsr), | 		ID($dffsr), | ||||||
|  | 		ID($dffsre), | ||||||
| 		ID($adff), | 		ID($adff), | ||||||
|  | 		ID($adffe), | ||||||
|  | 		ID($sdff), | ||||||
|  | 		ID($sdffe), | ||||||
|  | 		ID($sdffce), | ||||||
| 		ID($dlatch), | 		ID($dlatch), | ||||||
|  | 		ID($adlatch), | ||||||
| 		ID($dlatchsr), | 		ID($dlatchsr), | ||||||
| 		ID($_DFFE_NN_), | 		ID($_DFFE_NN_), | ||||||
| 		ID($_DFFE_NP_), | 		ID($_DFFE_NP_), | ||||||
|  | @ -69,16 +75,102 @@ const pool<IdString> &RTLIL::builtin_ff_cell_types() { | ||||||
| 		ID($_DFFSR_PNP_), | 		ID($_DFFSR_PNP_), | ||||||
| 		ID($_DFFSR_PPN_), | 		ID($_DFFSR_PPN_), | ||||||
| 		ID($_DFFSR_PPP_), | 		ID($_DFFSR_PPP_), | ||||||
|  | 		ID($_DFFSRE_NNNN_), | ||||||
|  | 		ID($_DFFSRE_NNNP_), | ||||||
|  | 		ID($_DFFSRE_NNPN_), | ||||||
|  | 		ID($_DFFSRE_NNPP_), | ||||||
|  | 		ID($_DFFSRE_NPNN_), | ||||||
|  | 		ID($_DFFSRE_NPNP_), | ||||||
|  | 		ID($_DFFSRE_NPPN_), | ||||||
|  | 		ID($_DFFSRE_NPPP_), | ||||||
|  | 		ID($_DFFSRE_PNNN_), | ||||||
|  | 		ID($_DFFSRE_PNNP_), | ||||||
|  | 		ID($_DFFSRE_PNPN_), | ||||||
|  | 		ID($_DFFSRE_PNPP_), | ||||||
|  | 		ID($_DFFSRE_PPNN_), | ||||||
|  | 		ID($_DFFSRE_PPNP_), | ||||||
|  | 		ID($_DFFSRE_PPPN_), | ||||||
|  | 		ID($_DFFSRE_PPPP_), | ||||||
|  | 		ID($_DFF_N_), | ||||||
|  | 		ID($_DFF_P_), | ||||||
| 		ID($_DFF_NN0_), | 		ID($_DFF_NN0_), | ||||||
| 		ID($_DFF_NN1_), | 		ID($_DFF_NN1_), | ||||||
| 		ID($_DFF_NP0_), | 		ID($_DFF_NP0_), | ||||||
| 		ID($_DFF_NP1_), | 		ID($_DFF_NP1_), | ||||||
| 		ID($_DFF_N_), |  | ||||||
| 		ID($_DFF_PN0_), | 		ID($_DFF_PN0_), | ||||||
| 		ID($_DFF_PN1_), | 		ID($_DFF_PN1_), | ||||||
| 		ID($_DFF_PP0_), | 		ID($_DFF_PP0_), | ||||||
| 		ID($_DFF_PP1_), | 		ID($_DFF_PP1_), | ||||||
| 		ID($_DFF_P_), | 		ID($_DFFE_NN0N_), | ||||||
|  | 		ID($_DFFE_NN0P_), | ||||||
|  | 		ID($_DFFE_NN1N_), | ||||||
|  | 		ID($_DFFE_NN1P_), | ||||||
|  | 		ID($_DFFE_NP0N_), | ||||||
|  | 		ID($_DFFE_NP0P_), | ||||||
|  | 		ID($_DFFE_NP1N_), | ||||||
|  | 		ID($_DFFE_NP1P_), | ||||||
|  | 		ID($_DFFE_PN0N_), | ||||||
|  | 		ID($_DFFE_PN0P_), | ||||||
|  | 		ID($_DFFE_PN1N_), | ||||||
|  | 		ID($_DFFE_PN1P_), | ||||||
|  | 		ID($_DFFE_PP0N_), | ||||||
|  | 		ID($_DFFE_PP0P_), | ||||||
|  | 		ID($_DFFE_PP1N_), | ||||||
|  | 		ID($_DFFE_PP1P_), | ||||||
|  | 		ID($_SDFF_NN0_), | ||||||
|  | 		ID($_SDFF_NN1_), | ||||||
|  | 		ID($_SDFF_NP0_), | ||||||
|  | 		ID($_SDFF_NP1_), | ||||||
|  | 		ID($_SDFF_PN0_), | ||||||
|  | 		ID($_SDFF_PN1_), | ||||||
|  | 		ID($_SDFF_PP0_), | ||||||
|  | 		ID($_SDFF_PP1_), | ||||||
|  | 		ID($_SDFFE_NN0N_), | ||||||
|  | 		ID($_SDFFE_NN0P_), | ||||||
|  | 		ID($_SDFFE_NN1N_), | ||||||
|  | 		ID($_SDFFE_NN1P_), | ||||||
|  | 		ID($_SDFFE_NP0N_), | ||||||
|  | 		ID($_SDFFE_NP0P_), | ||||||
|  | 		ID($_SDFFE_NP1N_), | ||||||
|  | 		ID($_SDFFE_NP1P_), | ||||||
|  | 		ID($_SDFFE_PN0N_), | ||||||
|  | 		ID($_SDFFE_PN0P_), | ||||||
|  | 		ID($_SDFFE_PN1N_), | ||||||
|  | 		ID($_SDFFE_PN1P_), | ||||||
|  | 		ID($_SDFFE_PP0N_), | ||||||
|  | 		ID($_SDFFE_PP0P_), | ||||||
|  | 		ID($_SDFFE_PP1N_), | ||||||
|  | 		ID($_SDFFE_PP1P_), | ||||||
|  | 		ID($_SDFFCE_NN0N_), | ||||||
|  | 		ID($_SDFFCE_NN0P_), | ||||||
|  | 		ID($_SDFFCE_NN1N_), | ||||||
|  | 		ID($_SDFFCE_NN1P_), | ||||||
|  | 		ID($_SDFFCE_NP0N_), | ||||||
|  | 		ID($_SDFFCE_NP0P_), | ||||||
|  | 		ID($_SDFFCE_NP1N_), | ||||||
|  | 		ID($_SDFFCE_NP1P_), | ||||||
|  | 		ID($_SDFFCE_PN0N_), | ||||||
|  | 		ID($_SDFFCE_PN0P_), | ||||||
|  | 		ID($_SDFFCE_PN1N_), | ||||||
|  | 		ID($_SDFFCE_PN1P_), | ||||||
|  | 		ID($_SDFFCE_PP0N_), | ||||||
|  | 		ID($_SDFFCE_PP0P_), | ||||||
|  | 		ID($_SDFFCE_PP1N_), | ||||||
|  | 		ID($_SDFFCE_PP1P_), | ||||||
|  | 		ID($_SR_NN_), | ||||||
|  | 		ID($_SR_NP_), | ||||||
|  | 		ID($_SR_PN_), | ||||||
|  | 		ID($_SR_PP_), | ||||||
|  | 		ID($_DLATCH_N_), | ||||||
|  | 		ID($_DLATCH_P_), | ||||||
|  | 		ID($_DLATCH_NN0_), | ||||||
|  | 		ID($_DLATCH_NN1_), | ||||||
|  | 		ID($_DLATCH_NP0_), | ||||||
|  | 		ID($_DLATCH_NP1_), | ||||||
|  | 		ID($_DLATCH_PN0_), | ||||||
|  | 		ID($_DLATCH_PN1_), | ||||||
|  | 		ID($_DLATCH_PP0_), | ||||||
|  | 		ID($_DLATCH_PP1_), | ||||||
| 		ID($_DLATCHSR_NNN_), | 		ID($_DLATCHSR_NNN_), | ||||||
| 		ID($_DLATCHSR_NNP_), | 		ID($_DLATCHSR_NNP_), | ||||||
| 		ID($_DLATCHSR_NPN_), | 		ID($_DLATCHSR_NPN_), | ||||||
|  | @ -87,8 +179,6 @@ const pool<IdString> &RTLIL::builtin_ff_cell_types() { | ||||||
| 		ID($_DLATCHSR_PNP_), | 		ID($_DLATCHSR_PNP_), | ||||||
| 		ID($_DLATCHSR_PPN_), | 		ID($_DLATCHSR_PPN_), | ||||||
| 		ID($_DLATCHSR_PPP_), | 		ID($_DLATCHSR_PPP_), | ||||||
| 		ID($_DLATCH_N_), |  | ||||||
| 		ID($_DLATCH_P_), |  | ||||||
| 		ID($_FF_), | 		ID($_FF_), | ||||||
| 	}; | 	}; | ||||||
| 	return res; | 	return res; | ||||||
|  | @ -1139,6 +1229,21 @@ namespace { | ||||||
| 				return; | 				return; | ||||||
| 			} | 			} | ||||||
| 
 | 
 | ||||||
|  | 			if (cell->type == ID($dffsre)) { | ||||||
|  | 				param_bool(ID::CLK_POLARITY); | ||||||
|  | 				param_bool(ID::SET_POLARITY); | ||||||
|  | 				param_bool(ID::CLR_POLARITY); | ||||||
|  | 				param_bool(ID::EN_POLARITY); | ||||||
|  | 				port(ID::CLK, 1); | ||||||
|  | 				port(ID::EN, 1); | ||||||
|  | 				port(ID::SET, param(ID::WIDTH)); | ||||||
|  | 				port(ID::CLR, param(ID::WIDTH)); | ||||||
|  | 				port(ID::D, param(ID::WIDTH)); | ||||||
|  | 				port(ID::Q, param(ID::WIDTH)); | ||||||
|  | 				check_expected(); | ||||||
|  | 				return; | ||||||
|  | 			} | ||||||
|  | 
 | ||||||
| 			if (cell->type == ID($adff)) { | 			if (cell->type == ID($adff)) { | ||||||
| 				param_bool(ID::CLK_POLARITY); | 				param_bool(ID::CLK_POLARITY); | ||||||
| 				param_bool(ID::ARST_POLARITY); | 				param_bool(ID::ARST_POLARITY); | ||||||
|  | @ -1151,6 +1256,46 @@ namespace { | ||||||
| 				return; | 				return; | ||||||
| 			} | 			} | ||||||
| 
 | 
 | ||||||
|  | 			if (cell->type == ID($sdff)) { | ||||||
|  | 				param_bool(ID::CLK_POLARITY); | ||||||
|  | 				param_bool(ID::SRST_POLARITY); | ||||||
|  | 				param_bits(ID::SRST_VALUE, param(ID::WIDTH)); | ||||||
|  | 				port(ID::CLK, 1); | ||||||
|  | 				port(ID::SRST, 1); | ||||||
|  | 				port(ID::D, param(ID::WIDTH)); | ||||||
|  | 				port(ID::Q, param(ID::WIDTH)); | ||||||
|  | 				check_expected(); | ||||||
|  | 				return; | ||||||
|  | 			} | ||||||
|  | 
 | ||||||
|  | 			if (cell->type.in(ID($sdffe), ID($sdffce))) { | ||||||
|  | 				param_bool(ID::CLK_POLARITY); | ||||||
|  | 				param_bool(ID::EN_POLARITY); | ||||||
|  | 				param_bool(ID::SRST_POLARITY); | ||||||
|  | 				param_bits(ID::SRST_VALUE, param(ID::WIDTH)); | ||||||
|  | 				port(ID::CLK, 1); | ||||||
|  | 				port(ID::EN, 1); | ||||||
|  | 				port(ID::SRST, 1); | ||||||
|  | 				port(ID::D, param(ID::WIDTH)); | ||||||
|  | 				port(ID::Q, param(ID::WIDTH)); | ||||||
|  | 				check_expected(); | ||||||
|  | 				return; | ||||||
|  | 			} | ||||||
|  | 
 | ||||||
|  | 			if (cell->type == ID($adffe)) { | ||||||
|  | 				param_bool(ID::CLK_POLARITY); | ||||||
|  | 				param_bool(ID::EN_POLARITY); | ||||||
|  | 				param_bool(ID::ARST_POLARITY); | ||||||
|  | 				param_bits(ID::ARST_VALUE, param(ID::WIDTH)); | ||||||
|  | 				port(ID::CLK, 1); | ||||||
|  | 				port(ID::EN, 1); | ||||||
|  | 				port(ID::ARST, 1); | ||||||
|  | 				port(ID::D, param(ID::WIDTH)); | ||||||
|  | 				port(ID::Q, param(ID::WIDTH)); | ||||||
|  | 				check_expected(); | ||||||
|  | 				return; | ||||||
|  | 			} | ||||||
|  | 
 | ||||||
| 			if (cell->type == ID($dlatch)) { | 			if (cell->type == ID($dlatch)) { | ||||||
| 				param_bool(ID::EN_POLARITY); | 				param_bool(ID::EN_POLARITY); | ||||||
| 				port(ID::EN, 1); | 				port(ID::EN, 1); | ||||||
|  | @ -1160,6 +1305,18 @@ namespace { | ||||||
| 				return; | 				return; | ||||||
| 			} | 			} | ||||||
| 
 | 
 | ||||||
|  | 			if (cell->type == ID($adlatch)) { | ||||||
|  | 				param_bool(ID::EN_POLARITY); | ||||||
|  | 				param_bool(ID::ARST_POLARITY); | ||||||
|  | 				param_bits(ID::ARST_VALUE, param(ID::WIDTH)); | ||||||
|  | 				port(ID::EN, 1); | ||||||
|  | 				port(ID::ARST, 1); | ||||||
|  | 				port(ID::D, param(ID::WIDTH)); | ||||||
|  | 				port(ID::Q, param(ID::WIDTH)); | ||||||
|  | 				check_expected(); | ||||||
|  | 				return; | ||||||
|  | 			} | ||||||
|  | 
 | ||||||
| 			if (cell->type == ID($dlatchsr)) { | 			if (cell->type == ID($dlatchsr)) { | ||||||
| 				param_bool(ID::EN_POLARITY); | 				param_bool(ID::EN_POLARITY); | ||||||
| 				param_bool(ID::SET_POLARITY); | 				param_bool(ID::SET_POLARITY); | ||||||
|  | @ -1351,49 +1508,69 @@ namespace { | ||||||
| 			if (cell->type == ID($_MUX8_))  { port(ID::A,1); port(ID::B,1); port(ID::C,1); port(ID::D,1); port(ID::E,1); port(ID::F,1); port(ID::G,1); port(ID::H,1); port(ID::S,1); port(ID::T,1); port(ID::U,1); port(ID::Y,1); check_expected(); return; } | 			if (cell->type == ID($_MUX8_))  { port(ID::A,1); port(ID::B,1); port(ID::C,1); port(ID::D,1); port(ID::E,1); port(ID::F,1); port(ID::G,1); port(ID::H,1); port(ID::S,1); port(ID::T,1); port(ID::U,1); port(ID::Y,1); check_expected(); return; } | ||||||
| 			if (cell->type == ID($_MUX16_)) { port(ID::A,1); port(ID::B,1); port(ID::C,1); port(ID::D,1); port(ID::E,1); port(ID::F,1); port(ID::G,1); port(ID::H,1); port(ID::I,1); port(ID::J,1); port(ID::K,1); port(ID::L,1); port(ID::M,1); port(ID::N,1); port(ID::O,1); port(ID::P,1); port(ID::S,1); port(ID::T,1); port(ID::U,1); port(ID::V,1); port(ID::Y,1); check_expected(); return; } | 			if (cell->type == ID($_MUX16_)) { port(ID::A,1); port(ID::B,1); port(ID::C,1); port(ID::D,1); port(ID::E,1); port(ID::F,1); port(ID::G,1); port(ID::H,1); port(ID::I,1); port(ID::J,1); port(ID::K,1); port(ID::L,1); port(ID::M,1); port(ID::N,1); port(ID::O,1); port(ID::P,1); port(ID::S,1); port(ID::T,1); port(ID::U,1); port(ID::V,1); port(ID::Y,1); check_expected(); return; } | ||||||
| 
 | 
 | ||||||
| 			if (cell->type == ID($_SR_NN_)) { port(ID::S,1); port(ID::R,1); port(ID::Q,1); check_expected(); return; } | 			if (cell->type.in(ID($_SR_NN_), ID($_SR_NP_), ID($_SR_PN_), ID($_SR_PP_))) | ||||||
| 			if (cell->type == ID($_SR_NP_)) { port(ID::S,1); port(ID::R,1); port(ID::Q,1); check_expected(); return; } | 				{ port(ID::S,1); port(ID::R,1); port(ID::Q,1); check_expected(); return; } | ||||||
| 			if (cell->type == ID($_SR_PN_)) { port(ID::S,1); port(ID::R,1); port(ID::Q,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_SR_PP_)) { port(ID::S,1); port(ID::R,1); port(ID::Q,1); check_expected(); return; } |  | ||||||
| 
 | 
 | ||||||
| 			if (cell->type == ID($_FF_))    { port(ID::D,1); port(ID::Q,1); check_expected();  return; } | 			if (cell->type == ID($_FF_)) { port(ID::D,1); port(ID::Q,1); check_expected();  return; } | ||||||
| 			if (cell->type == ID($_DFF_N_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFF_P_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); check_expected(); return; } |  | ||||||
| 
 | 
 | ||||||
| 			if (cell->type == ID($_DFFE_NN_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::E,1); check_expected(); return; } | 			if (cell->type.in(ID($_DFF_N_), ID($_DFF_P_))) | ||||||
| 			if (cell->type == ID($_DFFE_NP_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::E,1); check_expected(); return; } | 				{ port(ID::D,1); port(ID::Q,1); port(ID::C,1); check_expected(); return; } | ||||||
| 			if (cell->type == ID($_DFFE_PN_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::E,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFFE_PP_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::E,1); check_expected(); return; } |  | ||||||
| 
 | 
 | ||||||
| 			if (cell->type == ID($_DFF_NN0_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } | 			if (cell->type.in(ID($_DFFE_NN_), ID($_DFFE_NP_), ID($_DFFE_PN_), ID($_DFFE_PP_))) | ||||||
| 			if (cell->type == ID($_DFF_NN1_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } | 				{ port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::E,1); check_expected(); return; } | ||||||
| 			if (cell->type == ID($_DFF_NP0_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFF_NP1_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFF_PN0_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFF_PN1_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFF_PP0_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFF_PP1_)) { port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } |  | ||||||
| 
 | 
 | ||||||
| 			if (cell->type == ID($_DFFSR_NNN_)) { port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 			if (cell->type.in( | ||||||
| 			if (cell->type == ID($_DFFSR_NNP_)) { port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 					ID($_DFF_NN0_), ID($_DFF_NN1_), ID($_DFF_NP0_), ID($_DFF_NP1_), | ||||||
| 			if (cell->type == ID($_DFFSR_NPN_)) { port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 					ID($_DFF_PN0_), ID($_DFF_PN1_), ID($_DFF_PP0_), ID($_DFF_PP1_))) | ||||||
| 			if (cell->type == ID($_DFFSR_NPP_)) { port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 				{ port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } | ||||||
| 			if (cell->type == ID($_DFFSR_PNN_)) { port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFFSR_PNP_)) { port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFFSR_PPN_)) { port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } |  | ||||||
| 			if (cell->type == ID($_DFFSR_PPP_)) { port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } |  | ||||||
| 
 | 
 | ||||||
| 			if (cell->type == ID($_DLATCH_N_)) { port(ID::E,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 			if (cell->type.in( | ||||||
| 			if (cell->type == ID($_DLATCH_P_)) { port(ID::E,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 					ID($_DFFE_NN0N_), ID($_DFFE_NN0P_), ID($_DFFE_NN1N_), ID($_DFFE_NN1P_), | ||||||
|  | 					ID($_DFFE_NP0N_), ID($_DFFE_NP0P_), ID($_DFFE_NP1N_), ID($_DFFE_NP1P_), | ||||||
|  | 					ID($_DFFE_PN0N_), ID($_DFFE_PN0P_), ID($_DFFE_PN1N_), ID($_DFFE_PN1P_), | ||||||
|  | 					ID($_DFFE_PP0N_), ID($_DFFE_PP0P_), ID($_DFFE_PP1N_), ID($_DFFE_PP1P_))) | ||||||
|  | 				{ port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); port(ID::E,1); check_expected(); return; } | ||||||
| 
 | 
 | ||||||
| 			if (cell->type == ID($_DLATCHSR_NNN_)) { port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 			if (cell->type.in( | ||||||
| 			if (cell->type == ID($_DLATCHSR_NNP_)) { port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 					ID($_DFFSR_NNN_), ID($_DFFSR_NNP_), ID($_DFFSR_NPN_), ID($_DFFSR_NPP_), | ||||||
| 			if (cell->type == ID($_DLATCHSR_NPN_)) { port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 					ID($_DFFSR_PNN_), ID($_DFFSR_PNP_), ID($_DFFSR_PPN_), ID($_DFFSR_PPP_))) | ||||||
| 			if (cell->type == ID($_DLATCHSR_NPP_)) { port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 				{ port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | ||||||
| 			if (cell->type == ID($_DLATCHSR_PNN_)) { port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 
 | ||||||
| 			if (cell->type == ID($_DLATCHSR_PNP_)) { port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 			if (cell->type.in( | ||||||
| 			if (cell->type == ID($_DLATCHSR_PPN_)) { port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 					ID($_DFFSRE_NNNN_), ID($_DFFSRE_NNNP_), ID($_DFFSRE_NNPN_), ID($_DFFSRE_NNPP_), | ||||||
| 			if (cell->type == ID($_DLATCHSR_PPP_)) { port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | 					ID($_DFFSRE_NPNN_), ID($_DFFSRE_NPNP_), ID($_DFFSRE_NPPN_), ID($_DFFSRE_NPPP_), | ||||||
|  | 					ID($_DFFSRE_PNNN_), ID($_DFFSRE_PNNP_), ID($_DFFSRE_PNPN_), ID($_DFFSRE_PNPP_), | ||||||
|  | 					ID($_DFFSRE_PPNN_), ID($_DFFSRE_PPNP_), ID($_DFFSRE_PPPN_), ID($_DFFSRE_PPPP_))) | ||||||
|  | 				{ port(ID::C,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::E,1); port(ID::Q,1); check_expected(); return; } | ||||||
|  | 
 | ||||||
|  | 			if (cell->type.in( | ||||||
|  | 					ID($_SDFF_NN0_), ID($_SDFF_NN1_), ID($_SDFF_NP0_), ID($_SDFF_NP1_), | ||||||
|  | 					ID($_SDFF_PN0_), ID($_SDFF_PN1_), ID($_SDFF_PP0_), ID($_SDFF_PP1_))) | ||||||
|  | 				{ port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); check_expected(); return; } | ||||||
|  | 
 | ||||||
|  | 			if (cell->type.in( | ||||||
|  | 					ID($_SDFFE_NN0N_), ID($_SDFFE_NN0P_), ID($_SDFFE_NN1N_), ID($_SDFFE_NN1P_), | ||||||
|  | 					ID($_SDFFE_NP0N_), ID($_SDFFE_NP0P_), ID($_SDFFE_NP1N_), ID($_SDFFE_NP1P_), | ||||||
|  | 					ID($_SDFFE_PN0N_), ID($_SDFFE_PN0P_), ID($_SDFFE_PN1N_), ID($_SDFFE_PN1P_), | ||||||
|  | 					ID($_SDFFE_PP0N_), ID($_SDFFE_PP0P_), ID($_SDFFE_PP1N_), ID($_SDFFE_PP1P_), | ||||||
|  | 					ID($_SDFFCE_NN0N_), ID($_SDFFCE_NN0P_), ID($_SDFFCE_NN1N_), ID($_SDFFCE_NN1P_), | ||||||
|  | 					ID($_SDFFCE_NP0N_), ID($_SDFFCE_NP0P_), ID($_SDFFCE_NP1N_), ID($_SDFFCE_NP1P_), | ||||||
|  | 					ID($_SDFFCE_PN0N_), ID($_SDFFCE_PN0P_), ID($_SDFFCE_PN1N_), ID($_SDFFCE_PN1P_), | ||||||
|  | 					ID($_SDFFCE_PP0N_), ID($_SDFFCE_PP0P_), ID($_SDFFCE_PP1N_), ID($_SDFFCE_PP1P_))) | ||||||
|  | 				{ port(ID::D,1); port(ID::Q,1); port(ID::C,1); port(ID::R,1); port(ID::E,1); check_expected(); return; } | ||||||
|  | 
 | ||||||
|  | 			if (cell->type.in(ID($_DLATCH_N_), ID($_DLATCH_P_))) | ||||||
|  | 				{ port(ID::E,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | ||||||
|  | 
 | ||||||
|  | 			if (cell->type.in( | ||||||
|  | 					ID($_DLATCH_NN0_), ID($_DLATCH_NN1_), ID($_DLATCH_NP0_), ID($_DLATCH_NP1_), | ||||||
|  | 					ID($_DLATCH_PN0_), ID($_DLATCH_PN1_), ID($_DLATCH_PP0_), ID($_DLATCH_PP1_))) | ||||||
|  | 				{ port(ID::E,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | ||||||
|  | 
 | ||||||
|  | 			if (cell->type.in( | ||||||
|  | 					ID($_DLATCHSR_NNN_), ID($_DLATCHSR_NNP_), ID($_DLATCHSR_NPN_), ID($_DLATCHSR_NPP_), | ||||||
|  | 					ID($_DLATCHSR_PNN_), ID($_DLATCHSR_PNP_), ID($_DLATCHSR_PPN_), ID($_DLATCHSR_PPP_))) | ||||||
|  | 				{ port(ID::E,1); port(ID::S,1); port(ID::R,1); port(ID::D,1); port(ID::Q,1); check_expected(); return; } | ||||||
| 
 | 
 | ||||||
| 			error(__LINE__); | 			error(__LINE__); | ||||||
| 		} | 		} | ||||||
|  |  | ||||||
|  | @ -234,16 +234,6 @@ Clock is active on the positive edge if this parameter has the value {\tt 1'b1} | ||||||
| edge if this parameter is {\tt 1'b0}. | edge if this parameter is {\tt 1'b0}. | ||||||
| \end{itemize} | \end{itemize} | ||||||
| 
 | 
 | ||||||
| D-type flip-flops with enable are represented by {\tt \$dffe} cells. As the {\tt \$dff} |  | ||||||
| cells they have \B{CLK}, \B{D} and \B{Q} ports. In addition they also have a single-bit \B{EN} |  | ||||||
| input port for the enable pin and the following parameter: |  | ||||||
| 
 |  | ||||||
| \begin{itemize} |  | ||||||
| \item \B{EN\_POLARITY} \\ |  | ||||||
| The enable input is active-high if this parameter has the value {\tt 1'b1} and active-low |  | ||||||
| if this parameter is {\tt 1'b0}. |  | ||||||
| \end{itemize} |  | ||||||
| 
 |  | ||||||
| D-type flip-flops with asynchronous reset are represented by {\tt \$adff} cells. As the {\tt \$dff} | D-type flip-flops with asynchronous reset are represented by {\tt \$adff} cells. As the {\tt \$dff} | ||||||
| cells they have \B{CLK}, \B{D} and \B{Q} ports. In addition they also have a single-bit \B{ARST} | cells they have \B{CLK}, \B{D} and \B{Q} ports. In addition they also have a single-bit \B{ARST} | ||||||
| input port for the reset pin and the following additional two parameters: | input port for the reset pin and the following additional two parameters: | ||||||
|  | @ -257,13 +247,26 @@ if this parameter is {\tt 1'b0}. | ||||||
| The state of \B{Q} will be set to this value when the reset is active. | The state of \B{Q} will be set to this value when the reset is active. | ||||||
| \end{itemize} | \end{itemize} | ||||||
| 
 | 
 | ||||||
| Note that the {\tt \$adff} cell can only be used when the reset value is constant. |  | ||||||
| 
 |  | ||||||
| \begin{sloppypar} | \begin{sloppypar} | ||||||
| Usually these cells are generated by the {\tt proc} pass using the information | Usually these cells are generated by the {\tt proc} pass using the information | ||||||
| in the designs RTLIL::Process objects. | in the designs RTLIL::Process objects. | ||||||
| \end{sloppypar} | \end{sloppypar} | ||||||
| 
 | 
 | ||||||
|  | D-type flip-flops with synchronous reset are represented by {\tt \$sdff} cells. As the {\tt \$dff} | ||||||
|  | cells they have \B{CLK}, \B{D} and \B{Q} ports. In addition they also have a single-bit \B{SRST} | ||||||
|  | input port for the reset pin and the following additional two parameters: | ||||||
|  | 
 | ||||||
|  | \begin{itemize} | ||||||
|  | \item \B{SRST\_POLARITY} \\ | ||||||
|  | The synchronous reset is active-high if this parameter has the value {\tt 1'b1} and active-low | ||||||
|  | if this parameter is {\tt 1'b0}. | ||||||
|  | 
 | ||||||
|  | \item \B{SRST\_VALUE} \\ | ||||||
|  | The state of \B{Q} will be set to this value when the reset is active. | ||||||
|  | \end{itemize} | ||||||
|  | 
 | ||||||
|  | Note that the {\tt \$adff} and {\tt \$sdff} cells can only be used when the reset value is constant. | ||||||
|  | 
 | ||||||
| D-type flip-flops with asynchronous set and reset are represented by {\tt \$dffsr} cells. | D-type flip-flops with asynchronous set and reset are represented by {\tt \$dffsr} cells. | ||||||
| As the {\tt \$dff} cells they have \B{CLK}, \B{D} and \B{Q} ports. In addition they also have | As the {\tt \$dff} cells they have \B{CLK}, \B{D} and \B{Q} ports. In addition they also have | ||||||
| a single-bit \B{SET} input port for the set pin, a single-bit \B{CLR} input port for the reset pin, | a single-bit \B{SET} input port for the set pin, a single-bit \B{CLR} input port for the reset pin, | ||||||
|  | @ -282,9 +285,21 @@ if this parameter is {\tt 1'b0}. | ||||||
| When both the set and reset inputs of a {\tt \$dffsr} cell are active, the reset input takes | When both the set and reset inputs of a {\tt \$dffsr} cell are active, the reset input takes | ||||||
| precedence. | precedence. | ||||||
| 
 | 
 | ||||||
|  | D-type flip-flops with enable are represented by {\tt \$dffe}, {\tt \$adffe}, {\tt \$dffsre}, | ||||||
|  | {\tt \$sdffe}, and {\tt \$sdffce} cells, which are enhanced variants of {\tt \$dff}, {\tt \$adff}, {\tt \$dffsr}, | ||||||
|  | {\tt \$sdff} (with reset over enable) and {\tt \$sdff} (with enable over reset) | ||||||
|  | cells, respectively.  They have the same ports and parameters as their base cell. | ||||||
|  | In addition they also have a single-bit \B{EN} input port for the enable pin and the following parameter: | ||||||
|  | 
 | ||||||
|  | \begin{itemize} | ||||||
|  | \item \B{EN\_POLARITY} \\ | ||||||
|  | The enable input is active-high if this parameter has the value {\tt 1'b1} and active-low | ||||||
|  | if this parameter is {\tt 1'b0}. | ||||||
|  | \end{itemize} | ||||||
|  | 
 | ||||||
| \begin{fixme} | \begin{fixme} | ||||||
| Add information about {\tt \$sr} cells (set-reset flip-flops), {\tt \$dlatch} cells (d-type latches), | Add information about {\tt \$sr} cells (set-reset flip-flops), {\tt \$dlatch} cells (d-type latches), | ||||||
| and {\tt \$dlatchsr} cells (d-type latches with set/reset). | {\tt \$adlatch} and {\tt \$dlatchsr} cells (d-type latches with set/reset). | ||||||
| \end{fixme} | \end{fixme} | ||||||
| 
 | 
 | ||||||
| \subsection{Memories} | \subsection{Memories} | ||||||
|  | @ -490,20 +505,29 @@ Verilog & Cell Type \\ | ||||||
| \lstinline[language=Verilog]; always @(negedge C) Q <= D; & {\tt \$\_DFF\_N\_} \\ | \lstinline[language=Verilog]; always @(negedge C) Q <= D; & {\tt \$\_DFF\_N\_} \\ | ||||||
| \lstinline[language=Verilog]; always @(posedge C) Q <= D; & {\tt \$\_DFF\_P\_} \\ | \lstinline[language=Verilog]; always @(posedge C) Q <= D; & {\tt \$\_DFF\_P\_} \\ | ||||||
| \end{tabular} | \end{tabular} | ||||||
|  | \caption{Cell types for gate level logic networks (main list)} | ||||||
|  | \label{tab:CellLib_gates} | ||||||
|  | \end{table} | ||||||
|  | 
 | ||||||
|  | \begin{table}[t] | ||||||
| \hfil | \hfil | ||||||
| \begin{tabular}[t]{llll} | \begin{tabular}[t]{llll} | ||||||
| $ClkEdge$ & $RstLvl$ & $RstVal$ & Cell Type \\ | $ClkEdge$ & $RstLvl$ & $RstVal$ & Cell Type \\ | ||||||
| \hline | \hline | ||||||
| \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFF\_NN0\_} \\ | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFF\_NN0\_}, {\tt \$\_SDFF\_NN0\_} \\ | ||||||
| \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFF\_NN1\_} \\ | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFF\_NN1\_}, {\tt \$\_SDFF\_NN1\_} \\ | ||||||
| \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFF\_NP0\_} \\ | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFF\_NP0\_}, {\tt \$\_SDFF\_NP0\_} \\ | ||||||
| \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFF\_NP1\_} \\ | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFF\_NP1\_}, {\tt \$\_SDFF\_NP1\_} \\ | ||||||
| \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFF\_PN0\_} \\ | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFF\_PN0\_}, {\tt \$\_SDFF\_PN0\_} \\ | ||||||
| \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFF\_PN1\_} \\ | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFF\_PN1\_}, {\tt \$\_SDFF\_PN1\_} \\ | ||||||
| \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFF\_PP0\_} \\ | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFF\_PP0\_}, {\tt \$\_SDFF\_PP0\_} \\ | ||||||
| \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFF\_PP1\_} \\ | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFF\_PP1\_}, {\tt \$\_SDFF\_PP1\_} \\ | ||||||
| \end{tabular} | \end{tabular} | ||||||
| % FIXME: the layout of this is broken and I have no idea how to fix it | \caption{Cell types for gate level logic networks (FFs with reset)} | ||||||
|  | \label{tab:CellLib_gates_adff} | ||||||
|  | \end{table} | ||||||
|  | 
 | ||||||
|  | \begin{table}[t] | ||||||
| \hfil | \hfil | ||||||
| \begin{tabular}[t]{lll} | \begin{tabular}[t]{lll} | ||||||
| $ClkEdge$ & $EnLvl$ & Cell Type \\ | $ClkEdge$ & $EnLvl$ & Cell Type \\ | ||||||
|  | @ -513,7 +537,36 @@ $ClkEdge$ & $EnLvl$ & Cell Type \\ | ||||||
| \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_PN\_} \\ | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_PN\_} \\ | ||||||
| \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_PP\_} \\ | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_PP\_} \\ | ||||||
| \end{tabular} | \end{tabular} | ||||||
| % FIXME: the layout of this is broken too | \caption{Cell types for gate level logic networks (FFs with enable)} | ||||||
|  | \label{tab:CellLib_gates_dffe} | ||||||
|  | \end{table} | ||||||
|  | 
 | ||||||
|  | \begin{table}[t] | ||||||
|  | \begin{tabular}[t]{lllll} | ||||||
|  | $ClkEdge$ & $RstLvl$ & $RstVal$ & $EnLvl$ & Cell Type \\ | ||||||
|  | \hline | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_NN0N\_}, {\tt \$\_SDFFE\_NN0N\_}, {\tt \$\_SDFFCE\_NN0N\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_NN0P\_}, {\tt \$\_SDFFE\_NN0P\_}, {\tt \$\_SDFFCE\_NN0P\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_NN1N\_}, {\tt \$\_SDFFE\_NN1N\_}, {\tt \$\_SDFFCE\_NN1N\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_NN1P\_}, {\tt \$\_SDFFE\_NN1P\_}, {\tt \$\_SDFFCE\_NN1P\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_NP0N\_}, {\tt \$\_SDFFE\_NP0N\_}, {\tt \$\_SDFFCE\_NP0N\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_NP0P\_}, {\tt \$\_SDFFE\_NP0P\_}, {\tt \$\_SDFFCE\_NP0P\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_NP1N\_}, {\tt \$\_SDFFE\_NP1N\_}, {\tt \$\_SDFFCE\_NP1N\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_NP1P\_}, {\tt \$\_SDFFE\_NP1P\_}, {\tt \$\_SDFFCE\_NP1P\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_PN0N\_}, {\tt \$\_SDFFE\_PN0N\_}, {\tt \$\_SDFFCE\_PN0N\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_PN0P\_}, {\tt \$\_SDFFE\_PN0P\_}, {\tt \$\_SDFFCE\_PN0P\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_PN1N\_}, {\tt \$\_SDFFE\_PN1N\_}, {\tt \$\_SDFFCE\_PN1N\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_PN1P\_}, {\tt \$\_SDFFE\_PN1P\_}, {\tt \$\_SDFFCE\_PN1P\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_PP0N\_}, {\tt \$\_SDFFE\_PP0N\_}, {\tt \$\_SDFFCE\_PP0N\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_PP0P\_}, {\tt \$\_SDFFE\_PP0P\_}, {\tt \$\_SDFFCE\_PP0P\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFE\_PP1N\_}, {\tt \$\_SDFFE\_PP1N\_}, {\tt \$\_SDFFCE\_PP1N\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFE\_PP1P\_}, {\tt \$\_SDFFE\_PP1P\_}, {\tt \$\_SDFFCE\_PP1P\_} \\ | ||||||
|  | \end{tabular} | ||||||
|  | \caption{Cell types for gate level logic networks (FFs with reset and enable)} | ||||||
|  | \label{tab:CellLib_gates_adffe} | ||||||
|  | \end{table} | ||||||
|  | 
 | ||||||
|  | \begin{table}[t] | ||||||
| \hfil | \hfil | ||||||
| \begin{tabular}[t]{llll} | \begin{tabular}[t]{llll} | ||||||
| $ClkEdge$ & $SetLvl$ & $RstLvl$ & Cell Type \\ | $ClkEdge$ & $SetLvl$ & $RstLvl$ & Cell Type \\ | ||||||
|  | @ -527,11 +580,37 @@ $ClkEdge$ & $SetLvl$ & $RstLvl$ & Cell Type \\ | ||||||
| \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSR\_PPN\_} \\ | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSR\_PPN\_} \\ | ||||||
| \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSR\_PPP\_} \\ | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSR\_PPP\_} \\ | ||||||
| \end{tabular} | \end{tabular} | ||||||
| \caption{Cell types for gate level logic networks} | \caption{Cell types for gate level logic networks (FFs with set and reset)} | ||||||
| \label{tab:CellLib_gates} | \label{tab:CellLib_gates_dffsr} | ||||||
| \end{table} | \end{table} | ||||||
| 
 | 
 | ||||||
| Table~\ref{tab:CellLib_gates} lists all cell types used for gate level logic. The cell types | \begin{table}[t] | ||||||
|  | \hfil | ||||||
|  | \begin{tabular}[t]{lllll} | ||||||
|  | $ClkEdge$ & $SetLvl$ & $RstLvl$ & $EnLvl$ & Cell Type \\ | ||||||
|  | \hline | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSRE\_NNNN\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSRE\_NNNP\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSRE\_NNPN\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSRE\_NNPP\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSRE\_NPNN\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSRE\_NPNP\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSRE\_NPPN\_} \\ | ||||||
|  | \lstinline[language=Verilog];negedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSRE\_NPPP\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSRE\_PNNN\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSRE\_PNNP\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSRE\_PNPN\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSRE\_PNPP\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSRE\_PPNN\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSRE\_PPNP\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];0; & {\tt \$\_DFFSRE\_PPPN\_} \\ | ||||||
|  | \lstinline[language=Verilog];posedge; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & \lstinline[language=Verilog];1; & {\tt \$\_DFFSRE\_PPPP\_} \\ | ||||||
|  | \end{tabular} | ||||||
|  | \caption{Cell types for gate level logic networks (FFs with set and reset and enable)} | ||||||
|  | \label{tab:CellLib_gates_dffsre} | ||||||
|  | \end{table} | ||||||
|  | 
 | ||||||
|  | Tables~\ref{tab:CellLib_gates}, \ref{tab:CellLib_gates_dffe}, \ref{tab:CellLib_gates_adff}, \ref{tab:CellLib_gates_adffe}, \ref{tab:CellLib_gates_dffsr} and \ref{tab:CellLib_gates_dffsre} list all cell types used for gate level logic. The cell types | ||||||
| {\tt \$\_NOT\_}, {\tt \$\_AND\_}, {\tt \$\_NAND\_}, {\tt \$\_ANDNOT\_}, {\tt \$\_OR\_}, {\tt \$\_NOR\_}, | {\tt \$\_NOT\_}, {\tt \$\_AND\_}, {\tt \$\_NAND\_}, {\tt \$\_ANDNOT\_}, {\tt \$\_OR\_}, {\tt \$\_NOR\_}, | ||||||
| {\tt \$\_ORNOT\_}, {\tt \$\_XOR\_}, {\tt \$\_XNOR\_} and {\tt \$\_MUX\_} are used to model combinatorial logic. | {\tt \$\_ORNOT\_}, {\tt \$\_XOR\_}, {\tt \$\_XNOR\_} and {\tt \$\_MUX\_} are used to model combinatorial logic. | ||||||
| The cell type {\tt \$\_TBUF\_} is used to model tristate logic. | The cell type {\tt \$\_TBUF\_} is used to model tristate logic. | ||||||
|  | @ -563,8 +642,61 @@ otherwise. | ||||||
| 			Q <= D; | 			Q <= D; | ||||||
| \end{lstlisting} | \end{lstlisting} | ||||||
| 
 | 
 | ||||||
| The cell types {\tt \$\_DFFSR\_NNN\_}, {\tt \$\_DFFSR\_NNP\_}, {\tt \$\_DFFSR\_NPN\_}, {\tt \$\_DFFSR\_NPP\_}, | The cell types {\tt \$\_SDFF\_NN0\_}, {\tt \$\_SDFF\_NN1\_}, {\tt \$\_SDFF\_NP0\_}, {\tt \$\_SDFF\_NP1\_}, | ||||||
| {\tt \$\_DFFSR\_PNN\_}, {\tt \$\_DFFSR\_PNP\_}, {\tt \$\_DFFSR\_PPN\_} and {\tt \$\_DFFSR\_PPP\_} implement | {\tt \$\_SDFF\_PN0\_}, {\tt \$\_SDFF\_PN1\_}, {\tt \$\_SDFF\_PP0\_} and {\tt \$\_SDFF\_PP1\_} implement | ||||||
|  | d-type flip-flops with synchronous reset. The values in the table for these cell types relate to the | ||||||
|  | following Verilog code template: | ||||||
|  | 
 | ||||||
|  | \begin{lstlisting}[mathescape,language=Verilog] | ||||||
|  | 	always @($ClkEdge$ C) | ||||||
|  | 		if (R == $RstLvl$) | ||||||
|  | 			Q <= $RstVal$; | ||||||
|  | 		else | ||||||
|  | 			Q <= D; | ||||||
|  | \end{lstlisting} | ||||||
|  | 
 | ||||||
|  | The cell types {\tt \$\_DFFE\_[NP][NP][01][NP]\_} implement | ||||||
|  | d-type flip-flops with asynchronous reset and enable.  The values in the table for these cell types relate to the | ||||||
|  | following Verilog code template, where \lstinline[mathescape,language=Verilog];$RstEdge$; is \lstinline[language=Verilog];posedge; | ||||||
|  | if \lstinline[mathescape,language=Verilog];$RstLvl$; if \lstinline[language=Verilog];1;, and \lstinline[language=Verilog];negedge; | ||||||
|  | otherwise. | ||||||
|  | 
 | ||||||
|  | \begin{lstlisting}[mathescape,language=Verilog] | ||||||
|  | 	always @($ClkEdge$ C, $RstEdge$ R) | ||||||
|  | 		if (R == $RstLvl$) | ||||||
|  | 			Q <= $RstVal$; | ||||||
|  | 		else if (EN == $EnLvl$) | ||||||
|  | 			Q <= D; | ||||||
|  | \end{lstlisting} | ||||||
|  | 
 | ||||||
|  | The cell types {\tt \$\_SDFFE\_[NP][NP][01][NP]\_} implement d-type flip-flops | ||||||
|  | with synchronous reset and enable, with reset having priority over enable. | ||||||
|  | The values in the table for these cell types relate to the | ||||||
|  | following Verilog code template: | ||||||
|  | 
 | ||||||
|  | \begin{lstlisting}[mathescape,language=Verilog] | ||||||
|  | 	always @($ClkEdge$ C) | ||||||
|  | 		if (R == $RstLvl$) | ||||||
|  | 			Q <= $RstVal$; | ||||||
|  | 		else if (EN == $EnLvl$) | ||||||
|  | 			Q <= D; | ||||||
|  | \end{lstlisting} | ||||||
|  | 
 | ||||||
|  | The cell types {\tt \$\_SDFFCE\_[NP][NP][01][NP]\_} implement d-type flip-flops | ||||||
|  | with synchronous reset and enable, with enable having priority over reset. | ||||||
|  | The values in the table for these cell types relate to the | ||||||
|  | following Verilog code template: | ||||||
|  | 
 | ||||||
|  | \begin{lstlisting}[mathescape,language=Verilog] | ||||||
|  | 	always @($ClkEdge$ C) | ||||||
|  | 		if (EN == $EnLvl$) | ||||||
|  | 			if (R == $RstLvl$) | ||||||
|  | 				Q <= $RstVal$; | ||||||
|  | 			else | ||||||
|  | 				Q <= D; | ||||||
|  | \end{lstlisting} | ||||||
|  | 
 | ||||||
|  | The cell types {\tt \$\_DFFSR\_[NP][NP][NP]\_} implement | ||||||
| d-type flip-flops with asynchronous set and reset. The values in the table for these cell types relate to the | d-type flip-flops with asynchronous set and reset. The values in the table for these cell types relate to the | ||||||
| following Verilog code template, where \lstinline[mathescape,language=Verilog];$RstEdge$; is \lstinline[language=Verilog];posedge; | following Verilog code template, where \lstinline[mathescape,language=Verilog];$RstEdge$; is \lstinline[language=Verilog];posedge; | ||||||
| if \lstinline[mathescape,language=Verilog];$RstLvl$; if \lstinline[language=Verilog];1;, \lstinline[language=Verilog];negedge; | if \lstinline[mathescape,language=Verilog];$RstLvl$; if \lstinline[language=Verilog];1;, \lstinline[language=Verilog];negedge; | ||||||
|  | @ -582,6 +714,24 @@ otherwise. | ||||||
| 			Q <= D; | 			Q <= D; | ||||||
| \end{lstlisting} | \end{lstlisting} | ||||||
| 
 | 
 | ||||||
|  | The cell types {\tt \$\_DFFSRE\_[NP][NP][NP][NP]\_} implement | ||||||
|  | d-type flip-flops with asynchronous set and reset and enable. The values in the table for these cell types relate to the | ||||||
|  | following Verilog code template, where \lstinline[mathescape,language=Verilog];$RstEdge$; is \lstinline[language=Verilog];posedge; | ||||||
|  | if \lstinline[mathescape,language=Verilog];$RstLvl$; if \lstinline[language=Verilog];1;, \lstinline[language=Verilog];negedge; | ||||||
|  | otherwise, and \lstinline[mathescape,language=Verilog];$SetEdge$; is \lstinline[language=Verilog];posedge; | ||||||
|  | if \lstinline[mathescape,language=Verilog];$SetLvl$; if \lstinline[language=Verilog];1;, \lstinline[language=Verilog];negedge; | ||||||
|  | otherwise. | ||||||
|  | 
 | ||||||
|  | \begin{lstlisting}[mathescape,language=Verilog] | ||||||
|  | 	always @($ClkEdge$ C, $RstEdge$ R, $SetEdge$ S) | ||||||
|  | 		if (R == $RstLvl$) | ||||||
|  | 			Q <= 0; | ||||||
|  | 		else if (S == $SetLvl$) | ||||||
|  | 			Q <= 1; | ||||||
|  | 		else if (E == $EnLvl$) | ||||||
|  | 			Q <= D; | ||||||
|  | \end{lstlisting} | ||||||
|  | 
 | ||||||
| In most cases gate level logic networks are created from RTL networks using the {\tt techmap} pass. The flip-flop cells | In most cases gate level logic networks are created from RTL networks using the {\tt techmap} pass. The flip-flop cells | ||||||
| from the gate level logic network can be mapped to physical flip-flop cells from a Liberty file using the {\tt dfflibmap} | from the gate level logic network can be mapped to physical flip-flop cells from a Liberty file using the {\tt dfflibmap} | ||||||
| pass. The combinatorial logic cells can be mapped to physical cells from a Liberty file via ABC \citeweblink{ABC} | pass. The combinatorial logic cells can be mapped to physical cells from a Liberty file via ABC \citeweblink{ABC} | ||||||
|  |  | ||||||
|  | @ -117,7 +117,10 @@ struct statdata_t | ||||||
| 				} | 				} | ||||||
| 				else if (cell_type.in(ID($mux), ID($pmux))) | 				else if (cell_type.in(ID($mux), ID($pmux))) | ||||||
| 					cell_type = stringf("%s_%d", cell_type.c_str(), GetSize(cell->getPort(ID::Y))); | 					cell_type = stringf("%s_%d", cell_type.c_str(), GetSize(cell->getPort(ID::Y))); | ||||||
| 				else if (cell_type.in(ID($sr), ID($dff), ID($dffsr), ID($adff), ID($dlatch), ID($dlatchsr))) | 				else if (cell_type.in( | ||||||
|  | 						ID($sr), ID($ff), ID($dff), ID($dffe), ID($dffsr), ID($dffsre), | ||||||
|  | 						ID($adff), ID($adffe), ID($sdff), ID($sdffe), ID($sdffce), | ||||||
|  | 						ID($dlatch), ID($adlatch), ID($dlatchsr))) | ||||||
| 					cell_type = stringf("%s_%d", cell_type.c_str(), GetSize(cell->getPort(ID::Q))); | 					cell_type = stringf("%s_%d", cell_type.c_str(), GetSize(cell->getPort(ID::Q))); | ||||||
| 			} | 			} | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
|  | @ -108,6 +108,31 @@ endmodule | ||||||
| """ | """ | ||||||
| //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
| //- | //- | ||||||
|  | //-     $_DFFE_{C:N|P}{R:N|P}{V:0|1}{E:N|P}_ (D, C, R, E, Q) | ||||||
|  | //- | ||||||
|  | //- A {C:negative|positive} edge D-type flip-flop with {R:negative|positive} polarity {V:reset|set} and {E:negative|positive} | ||||||
|  | //- polarity clock enable. | ||||||
|  | //- | ||||||
|  | //- Truth table:    D C R E | Q | ||||||
|  | //-                ---------+--- | ||||||
|  | //-                 - - {R:0|1} - | {V:0|1} | ||||||
|  | //-                 d {C:\\|/} - {E:0|1} | d | ||||||
|  | //-                 - - - - | q | ||||||
|  | //- | ||||||
|  | module \$_DFFE_{C:N|P}{R:N|P}{V:0|1}{E:N|P}_ (D, C, R, E, Q); | ||||||
|  | input D, C, R, E; | ||||||
|  | output reg Q; | ||||||
|  | always @({C:neg|pos}edge C or {R:neg|pos}edge R) begin | ||||||
|  | 	if (R == {R:0|1}) | ||||||
|  | 		Q <= {V:0|1}; | ||||||
|  | 	else if (E == {E:0|1}) | ||||||
|  | 		Q <= D; | ||||||
|  | end | ||||||
|  | endmodule | ||||||
|  | """, | ||||||
|  | """ | ||||||
|  | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
|  | //- | ||||||
| //-     $_DFFSR_{C:N|P}{S:N|P}{R:N|P}_ (C, S, R, D, Q) | //-     $_DFFSR_{C:N|P}{S:N|P}{R:N|P}_ (C, S, R, D, Q) | ||||||
| //- | //- | ||||||
| //- A {C:negative|positive} edge D-type flip-flop with {S:negative|positive} polarity set and {R:negative|positive} | //- A {C:negative|positive} edge D-type flip-flop with {S:negative|positive} polarity set and {R:negative|positive} | ||||||
|  | @ -136,6 +161,110 @@ endmodule | ||||||
| """ | """ | ||||||
| //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
| //- | //- | ||||||
|  | //-     $_DFFSRE_{C:N|P}{S:N|P}{R:N|P}{E:N|P}_ (C, S, R, E, D, Q) | ||||||
|  | //- | ||||||
|  | //- A {C:negative|positive} edge D-type flip-flop with {S:negative|positive} polarity set, {R:negative|positive} | ||||||
|  | //- polarity reset and {E:negative|positive} polarity clock enable. | ||||||
|  | //- | ||||||
|  | //- Truth table:    C S R E D | Q | ||||||
|  | //-                -----------+--- | ||||||
|  | //-                 - - {R:0|1} - - | 0 | ||||||
|  | //-                 - {S:0|1} - - - | 1 | ||||||
|  | //-                 {C:\\|/} - - {E:0|1} d | d | ||||||
|  | //-                 - - - - - | q | ||||||
|  | //- | ||||||
|  | module \$_DFFSRE_{C:N|P}{S:N|P}{R:N|P}{E:N|P}_ (C, S, R, E, D, Q); | ||||||
|  | input C, S, R, E, D; | ||||||
|  | output reg Q; | ||||||
|  | always @({C:neg|pos}edge C, {S:neg|pos}edge S, {R:neg|pos}edge R) begin | ||||||
|  | 	if (R == {R:0|1}) | ||||||
|  | 		Q <= 0; | ||||||
|  | 	else if (S == {S:0|1}) | ||||||
|  | 		Q <= 1; | ||||||
|  |         else if (E == {E:0|1}) | ||||||
|  | 		Q <= D; | ||||||
|  | end | ||||||
|  | endmodule | ||||||
|  | """, | ||||||
|  | """ | ||||||
|  | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
|  | //- | ||||||
|  | //-     $_SDFF_{C:N|P}{R:N|P}{V:0|1}_ (D, C, R, Q) | ||||||
|  | //- | ||||||
|  | //- A {C:negative|positive} edge D-type flip-flop with {R:negative|positive} polarity synchronous {V:reset|set}. | ||||||
|  | //- | ||||||
|  | //- Truth table:    D C R | Q | ||||||
|  | //-                -------+--- | ||||||
|  | //-                 - {C:\\|/} {R:0|1} | {V:0|1} | ||||||
|  | //-                 d {C:\\|/} - | d | ||||||
|  | //-                 - - - | q | ||||||
|  | //- | ||||||
|  | module \$_SDFF_{C:N|P}{R:N|P}{V:0|1}_ (D, C, R, Q); | ||||||
|  | input D, C, R; | ||||||
|  | output reg Q; | ||||||
|  | always @({C:neg|pos}edge C) begin | ||||||
|  | 	if (R == {R:0|1}) | ||||||
|  | 		Q <= {V:0|1}; | ||||||
|  | 	else | ||||||
|  | 		Q <= D; | ||||||
|  | end | ||||||
|  | endmodule | ||||||
|  | """, | ||||||
|  | """ | ||||||
|  | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
|  | //- | ||||||
|  | //-     $_SDFFE_{C:N|P}{R:N|P}{V:0|1}{E:N|P}_ (D, C, R, E, Q) | ||||||
|  | //- | ||||||
|  | //- A {C:negative|positive} edge D-type flip-flop with {R:negative|positive} polarity synchronous {V:reset|set} and {E:negative|positive} | ||||||
|  | //- polarity clock enable (with {V:reset|set} having priority). | ||||||
|  | //- | ||||||
|  | //- Truth table:    D C R E | Q | ||||||
|  | //-                ---------+--- | ||||||
|  | //-                 - {C:\\|/} {R:0|1} - | {V:0|1} | ||||||
|  | //-                 d {C:\\|/} - {E:0|1} | d | ||||||
|  | //-                 - - - - | q | ||||||
|  | //- | ||||||
|  | module \$_SDFFE_{C:N|P}{R:N|P}{V:0|1}{E:N|P}_ (D, C, R, E, Q); | ||||||
|  | input D, C, R, E; | ||||||
|  | output reg Q; | ||||||
|  | always @({C:neg|pos}edge C) begin | ||||||
|  | 	if (R == {R:0|1}) | ||||||
|  | 		Q <= {V:0|1}; | ||||||
|  | 	else if (E == {E:0|1}) | ||||||
|  | 		Q <= D; | ||||||
|  | end | ||||||
|  | endmodule | ||||||
|  | """, | ||||||
|  | """ | ||||||
|  | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
|  | //- | ||||||
|  | //-     $_SDFFCE_{C:N|P}{R:N|P}{V:0|1}{E:N|P}_ (D, C, R, E, Q) | ||||||
|  | //- | ||||||
|  | //- A {C:negative|positive} edge D-type flip-flop with {R:negative|positive} polarity synchronous {V:reset|set} and {E:negative|positive} | ||||||
|  | //- polarity clock enable (with clock enable having priority). | ||||||
|  | //- | ||||||
|  | //- Truth table:    D C R E | Q | ||||||
|  | //-                ---------+--- | ||||||
|  | //-                 - {C:\\|/} {R:0|1} {E:0|1} | {V:0|1} | ||||||
|  | //-                 d {C:\\|/} - {E:0|1} | d | ||||||
|  | //-                 - - - - | q | ||||||
|  | //- | ||||||
|  | module \$_SDFFCE_{C:N|P}{R:N|P}{V:0|1}{E:N|P}_ (D, C, R, E, Q); | ||||||
|  | input D, C, R, E; | ||||||
|  | output reg Q; | ||||||
|  | always @({C:neg|pos}edge C) begin | ||||||
|  | 	if (E == {E:0|1}) begin | ||||||
|  | 		if (R == {R:0|1}) | ||||||
|  | 			Q <= {V:0|1}; | ||||||
|  | 		else | ||||||
|  | 			Q <= D; | ||||||
|  | 	end | ||||||
|  | end | ||||||
|  | endmodule | ||||||
|  | """, | ||||||
|  | """ | ||||||
|  | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
|  | //- | ||||||
| //-     $_DLATCH_{E:N|P}_ (E, D, Q) | //-     $_DLATCH_{E:N|P}_ (E, D, Q) | ||||||
| //- | //- | ||||||
| //- A {E:negative|positive} enable D-type latch. | //- A {E:negative|positive} enable D-type latch. | ||||||
|  | @ -157,6 +286,30 @@ endmodule | ||||||
| """ | """ | ||||||
| //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
| //- | //- | ||||||
|  | //-     $_DLATCH_{E:N|P}{R:N|P}{V:0|1}_ (E, R, D, Q) | ||||||
|  | //- | ||||||
|  | //- A {E:negative|positive} enable D-type latch with {R:negative|positive} polarity {V:reset|set}. | ||||||
|  | //- | ||||||
|  | //- Truth table:    E R D | Q | ||||||
|  | //-                -------+--- | ||||||
|  | //-                 - {R:0|1} - | {V:0|1} | ||||||
|  | //-                 {E:0|1} - d | d | ||||||
|  | //-                 - - - | q | ||||||
|  | //- | ||||||
|  | module \$_DLATCH_{E:N|P}{R:N|P}{V:0|1}_ (E, R, D, Q); | ||||||
|  | input E, R, D; | ||||||
|  | output reg Q; | ||||||
|  | always @* begin | ||||||
|  | 	if (R == {E:0|1}) | ||||||
|  |                 Q <= {V:0|1}; | ||||||
|  | 	else if (E == {E:0|1}) | ||||||
|  | 		Q <= D; | ||||||
|  | end | ||||||
|  | endmodule | ||||||
|  | """, | ||||||
|  | """ | ||||||
|  | //  |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| | ||||||
|  | //- | ||||||
| //-     $_DLATCHSR_{E:N|P}{S:N|P}{R:N|P}_ (E, S, R, D, Q) | //-     $_DLATCHSR_{E:N|P}{S:N|P}{R:N|P}_ (E, S, R, D, Q) | ||||||
| //- | //- | ||||||
| //- A {E:negative|positive} enable D-type latch with {S:negative|positive} polarity set and {R:negative|positive} | //- A {E:negative|positive} enable D-type latch with {S:negative|positive} polarity set and {R:negative|positive} | ||||||
|  |  | ||||||
										
											
												File diff suppressed because it is too large
												Load diff
											
										
									
								
							|  | @ -1822,6 +1822,39 @@ endgenerate | ||||||
| 
 | 
 | ||||||
| endmodule | endmodule | ||||||
| 
 | 
 | ||||||
|  | // --------------------------------------------------------
 | ||||||
|  | 
 | ||||||
|  | module \$dffsre (CLK, SET, CLR, EN, D, Q); | ||||||
|  | 
 | ||||||
|  | parameter WIDTH = 0; | ||||||
|  | parameter CLK_POLARITY = 1'b1; | ||||||
|  | parameter SET_POLARITY = 1'b1; | ||||||
|  | parameter CLR_POLARITY = 1'b1; | ||||||
|  | parameter EN_POLARITY = 1'b1; | ||||||
|  | 
 | ||||||
|  | input CLK, EN; | ||||||
|  | input [WIDTH-1:0] SET, CLR, D; | ||||||
|  | output reg [WIDTH-1:0] Q; | ||||||
|  | 
 | ||||||
|  | wire pos_clk = CLK == CLK_POLARITY; | ||||||
|  | wire [WIDTH-1:0] pos_set = SET_POLARITY ? SET : ~SET; | ||||||
|  | wire [WIDTH-1:0] pos_clr = CLR_POLARITY ? CLR : ~CLR; | ||||||
|  | 
 | ||||||
|  | genvar i; | ||||||
|  | generate | ||||||
|  | 	for (i = 0; i < WIDTH; i = i+1) begin:bitslices | ||||||
|  | 		always @(posedge pos_set[i], posedge pos_clr[i], posedge pos_clk) | ||||||
|  | 			if (pos_clr[i]) | ||||||
|  | 				Q[i] <= 0; | ||||||
|  | 			else if (pos_set[i]) | ||||||
|  | 				Q[i] <= 1; | ||||||
|  | 			else if (EN == EN_POLARITY) | ||||||
|  | 				Q[i] <= D[i]; | ||||||
|  | 	end | ||||||
|  | endgenerate | ||||||
|  | 
 | ||||||
|  | endmodule | ||||||
|  | 
 | ||||||
| `endif | `endif | ||||||
| // --------------------------------------------------------
 | // --------------------------------------------------------
 | ||||||
| 
 | 
 | ||||||
|  | @ -1849,6 +1882,107 @@ endmodule | ||||||
| 
 | 
 | ||||||
| // --------------------------------------------------------
 | // --------------------------------------------------------
 | ||||||
| 
 | 
 | ||||||
|  | module \$sdff (CLK, SRST, D, Q); | ||||||
|  | 
 | ||||||
|  | parameter WIDTH = 0; | ||||||
|  | parameter CLK_POLARITY = 1'b1; | ||||||
|  | parameter SRST_POLARITY = 1'b1; | ||||||
|  | parameter SRST_VALUE = 0; | ||||||
|  | 
 | ||||||
|  | input CLK, SRST; | ||||||
|  | input [WIDTH-1:0] D; | ||||||
|  | output reg [WIDTH-1:0] Q; | ||||||
|  | wire pos_clk = CLK == CLK_POLARITY; | ||||||
|  | wire pos_srst = SRST == SRST_POLARITY; | ||||||
|  | 
 | ||||||
|  | always @(posedge pos_clk) begin | ||||||
|  | 	if (pos_srst) | ||||||
|  | 		Q <= SRST_VALUE; | ||||||
|  | 	else | ||||||
|  | 		Q <= D; | ||||||
|  | end | ||||||
|  | 
 | ||||||
|  | endmodule | ||||||
|  | 
 | ||||||
|  | // --------------------------------------------------------
 | ||||||
|  | 
 | ||||||
|  | module \$adffe (CLK, ARST, EN, D, Q); | ||||||
|  | 
 | ||||||
|  | parameter WIDTH = 0; | ||||||
|  | parameter CLK_POLARITY = 1'b1; | ||||||
|  | parameter EN_POLARITY = 1'b1; | ||||||
|  | parameter ARST_POLARITY = 1'b1; | ||||||
|  | parameter ARST_VALUE = 0; | ||||||
|  | 
 | ||||||
|  | input CLK, ARST, EN; | ||||||
|  | input [WIDTH-1:0] D; | ||||||
|  | output reg [WIDTH-1:0] Q; | ||||||
|  | wire pos_clk = CLK == CLK_POLARITY; | ||||||
|  | wire pos_arst = ARST == ARST_POLARITY; | ||||||
|  | 
 | ||||||
|  | always @(posedge pos_clk, posedge pos_arst) begin | ||||||
|  | 	if (pos_arst) | ||||||
|  | 		Q <= ARST_VALUE; | ||||||
|  | 	else if (EN == EN_POLARITY) | ||||||
|  | 		Q <= D; | ||||||
|  | end | ||||||
|  | 
 | ||||||
|  | endmodule | ||||||
|  | 
 | ||||||
|  | // --------------------------------------------------------
 | ||||||
|  | 
 | ||||||
|  | module \$sdffe (CLK, SRST, EN, D, Q); | ||||||
|  | 
 | ||||||
|  | parameter WIDTH = 0; | ||||||
|  | parameter CLK_POLARITY = 1'b1; | ||||||
|  | parameter EN_POLARITY = 1'b1; | ||||||
|  | parameter SRST_POLARITY = 1'b1; | ||||||
|  | parameter SRST_VALUE = 0; | ||||||
|  | 
 | ||||||
|  | input CLK, SRST, EN; | ||||||
|  | input [WIDTH-1:0] D; | ||||||
|  | output reg [WIDTH-1:0] Q; | ||||||
|  | wire pos_clk = CLK == CLK_POLARITY; | ||||||
|  | wire pos_srst = SRST == SRST_POLARITY; | ||||||
|  | 
 | ||||||
|  | always @(posedge pos_clk) begin | ||||||
|  | 	if (pos_srst) | ||||||
|  | 		Q <= SRST_VALUE; | ||||||
|  | 	else if (EN == EN_POLARITY) | ||||||
|  | 		Q <= D; | ||||||
|  | end | ||||||
|  | 
 | ||||||
|  | endmodule | ||||||
|  | 
 | ||||||
|  | // --------------------------------------------------------
 | ||||||
|  | 
 | ||||||
|  | module \$sdffce (CLK, SRST, EN, D, Q); | ||||||
|  | 
 | ||||||
|  | parameter WIDTH = 0; | ||||||
|  | parameter CLK_POLARITY = 1'b1; | ||||||
|  | parameter EN_POLARITY = 1'b1; | ||||||
|  | parameter SRST_POLARITY = 1'b1; | ||||||
|  | parameter SRST_VALUE = 0; | ||||||
|  | 
 | ||||||
|  | input CLK, SRST, EN; | ||||||
|  | input [WIDTH-1:0] D; | ||||||
|  | output reg [WIDTH-1:0] Q; | ||||||
|  | wire pos_clk = CLK == CLK_POLARITY; | ||||||
|  | wire pos_srst = SRST == SRST_POLARITY; | ||||||
|  | 
 | ||||||
|  | always @(posedge pos_clk) begin | ||||||
|  | 	if (EN == EN_POLARITY) begin | ||||||
|  | 		if (pos_srst) | ||||||
|  | 			Q <= SRST_VALUE; | ||||||
|  | 		else | ||||||
|  | 			Q <= D; | ||||||
|  | 	end | ||||||
|  | end | ||||||
|  | 
 | ||||||
|  | endmodule | ||||||
|  | 
 | ||||||
|  | // --------------------------------------------------------
 | ||||||
|  | 
 | ||||||
| module \$dlatch (EN, D, Q); | module \$dlatch (EN, D, Q); | ||||||
| 
 | 
 | ||||||
| parameter WIDTH = 0; | parameter WIDTH = 0; | ||||||
|  | @ -1865,6 +1999,28 @@ end | ||||||
| 
 | 
 | ||||||
| endmodule | endmodule | ||||||
| 
 | 
 | ||||||
|  | // --------------------------------------------------------
 | ||||||
|  | 
 | ||||||
|  | module \$adlatch (EN, ARST, D, Q); | ||||||
|  | 
 | ||||||
|  | parameter WIDTH = 0; | ||||||
|  | parameter EN_POLARITY = 1'b1; | ||||||
|  | parameter ARST_POLARITY = 1'b1; | ||||||
|  | parameter ARST_VALUE = 0; | ||||||
|  | 
 | ||||||
|  | input EN, ARST; | ||||||
|  | input [WIDTH-1:0] D; | ||||||
|  | output reg [WIDTH-1:0] Q; | ||||||
|  | 
 | ||||||
|  | always @* begin | ||||||
|  | 	if (ARST == ARST_POLARITY) | ||||||
|  | 		Q = ARST_VALUE; | ||||||
|  | 	else if (EN == EN_POLARITY) | ||||||
|  | 		Q = D; | ||||||
|  | end | ||||||
|  | 
 | ||||||
|  | endmodule | ||||||
|  | 
 | ||||||
| // --------------------------------------------------------
 | // --------------------------------------------------------
 | ||||||
| `ifndef SIMLIB_NOSR | `ifndef SIMLIB_NOSR | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue