1
0
mirror of https://github.com/Gehstock/Mist_FPGA.git synced 2026-01-13 23:26:43 +00:00

Sound Fix

This commit is contained in:
Gehstock 2018-12-02 16:50:20 +01:00
parent 9c41b57dd9
commit 1fe7ca8a0b
14 changed files with 570 additions and 182 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 39 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 39 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 78 KiB

View File

@ -218,4 +218,7 @@ set_global_assignment -name PARTITION_COLOR 16764057 -section_id Top
# end ENTITY(Galaksija_MiST)
# --------------------------
set_global_assignment -name SYSTEMVERILOG_FILE rtl/galaksija_keyboard1.sv
set_global_assignment -name SYSTEMVERILOG_FILE rtl/galaksija_keyboard2.sv
set_global_assignment -name VHDL_FILE rtl/keyboard.vhd
set_instance_assignment -name PARTITION_HIERARCHY root_partition -to | -section_id Top

View File

@ -4,4 +4,4 @@ VGA Only
32k Ram
Rom 1+2+3
AY8910
AY8912

View File

@ -21,9 +21,7 @@ module Galaksija_MiST(
`include "build_id.v"
localparam CONF_STR = {
"Galaksija;;",
// "F,GAL,Load Program;",
"O23,Scandoubler Fx,None,HQ2x,CRT 25%,CRT 50%;",
"O4,Sound,Off,On;",
"T9,Reset;",
"V,v1.00.",`BUILD_DATE
};
@ -38,6 +36,8 @@ wire forced_scandoubler;
wire [31:0] status;
wire [7:0] audio;
wire [10:0] ps2_key;
wire ps2_clk;
wire ps2_data;
assign LED = 1'b1;
pll pll (
@ -63,7 +63,9 @@ user_io (
.scandoubler_disable(forced_scandoubler),
.buttons(buttons),
.switches(switches),
.ps2_key(ps2_key)
.ps2_key(ps2_key),
.ps2_kbd_clk(ps2_clk),
.ps2_kbd_data(ps2_data)
);
video_mixer #(
@ -87,19 +89,23 @@ video_mixer (
.VGA_VS ( VGA_VS ),
.VGA_HS ( VGA_HS ),
.scanlines (forced_scandoubler ? 2'b00 : {status[3:2] == 3, status[3:2] == 2}),
.scandoubler_disable(1'b1),//forced_scandoubler),
.scandoubler_disable(1'b1),
.hq2x (status[3:2]==1),
.ypbpr ( ypbpr ),
.ypbpr_full ( 1 ),
.line_start ( 0 ),
.mono ( 1 )
);
wire [7:0] video;
wire [7:0] video;
galaksija_top galaksija_top (
.sysclk(clk_25),
.vidclk(clk_25),
.cpuclk(clk_6p25),
.audclk(clk_1p7),
.reset_in(~(status[0] | status[9] | buttons[1])),
.ps2_key(ps2_key),
.ps2_clk(ps2_clk),
.ps2_data(ps2_data),
.audio(audio),
.cass_in(UART_RXD),
.cass_out(UART_TXD),
@ -113,7 +119,7 @@ dac #(
.msbi_g(7))
dac (
.clk_i(clk_25),
.res_n_i(status[4] ? 1'b1 : 1'b0),
.res_n_i(1'b1),
.dac_i(audio),
.dac_o(AUDIO_L)
);

View File

@ -1,2 +1,2 @@
`define BUILD_DATE "181202"
`define BUILD_TIME "114154"
`define BUILD_TIME "164146"

View File

@ -0,0 +1,127 @@
module galaksija_keyboard1(
input clk,
input reset,
input [5:0]addr,
input [7:0]ps2_key,
output [7:0]key_out,
input rd_key
);
integer num;
reg [63:0]keys;
initial
begin
for(num=0;num<64;num=num+1)
begin
keys[num] <= 0;
end
end
always @(posedge clk) begin
for(num=0;num<64;num=num+1)
begin
keys[num] = 1'b0;
end
case (ps2_key[7:0])
//nix 00
8'h1C : keys[8'd01] = 1'b1; // A
8'h32 : keys[8'd02] = 1'b1; // B
8'h21 : keys[8'd03] = 1'b1; // C
8'h23 : keys[8'd04] = 1'b1; // D
8'h24 : keys[8'd05] = 1'b1; // E
8'h2B : keys[8'd06] = 1'b1; // F
8'h34 : keys[8'd07] = 1'b1; // G
8'h33 : keys[8'd08] = 1'b1; // H
8'h43 : keys[8'd09] = 1'b1; // I
8'h3B : keys[8'd10] = 1'b1; // J
8'h42 : keys[8'd11] = 1'b1; // K
8'h4B : keys[8'd12] = 1'b1; // L
8'h3A : keys[8'd13] = 1'b1; // M
8'h31 : keys[8'd14] = 1'b1; // N
8'h44 : keys[8'd15] = 1'b1; // O
8'h4D : keys[8'd16] = 1'b1; // P
8'h15 : keys[8'd17] = 1'b1; // Q
8'h2D : keys[8'd18] = 1'b1; // R
8'h1B : keys[8'd19] = 1'b1; // S
8'h2C : keys[8'd20] = 1'b1; // T
8'h3C : keys[8'd21] = 1'b1; // U
8'h2A : keys[8'd22] = 1'b1; // V
8'h1D : keys[8'd23] = 1'b1; // W
8'h22 : keys[8'd24] = 1'b1; // X
8'h35 : keys[8'd25] = 1'b1; // Y
8'h1A : keys[8'd26] = 1'b1; // Z
//nix 27,28
8'h66 : keys[8'd29] = 1'b1; // BACKSPACE
//nix 30
8'h29 : keys[8'd31] = 1'b1; // SPACE
8'h45 : keys[8'd32] = 1'b1; // 0
8'h16 : keys[8'd33] = 1'b1; // 1
8'h1E : keys[8'd34] = 1'b1; // 2
8'h26 : keys[8'd35] = 1'b1; // 3
8'h25 : keys[8'd36] = 1'b1; // 4
8'h2E : keys[8'd37] = 1'b1; // 5
8'h36 : keys[8'd38] = 1'b1; // 6
8'h3D : keys[8'd39] = 1'b1; // 7
8'h3E : keys[8'd40] = 1'b1; // 8
8'h46 : keys[8'd41] = 1'b1; // 9
// NUM Block
8'h70 : keys[8'd32] = 1'b1; // 0
8'h69 : keys[8'd33] = 1'b1; // 1
8'h72 : keys[8'd34] = 1'b1; // 2
8'h7A : keys[8'd35] = 1'b1; // 3
8'h6B : keys[8'd36] = 1'b1; // 4
8'h73 : keys[8'd37] = 1'b1; // 5
8'h74 : keys[8'd38] = 1'b1; // 6
8'h6C : keys[8'd39] = 1'b1; // 7
8'h75 : keys[8'd40] = 1'b1; // 8
8'h7D : keys[8'd41] = 1'b1; // 9
8'h4C : keys[8'd42] = 1'b1; // ; //todo "Ö" on german keyboard
8'h7C : keys[8'd43] = 1'b1; // : //todo NUM block for now
8'h41 : keys[8'd44] = 1'b1; // ,
8'h55 : keys[8'd45] = 1'b1; // = ////todo "´" on german keyboard
8'h49 : keys[8'd46] = 1'b1; // .
8'h4A : keys[8'd47] = 1'b1; // /
8'h5A : keys[8'd48] = 1'b1; // ENTER
8'h76 : keys[8'd49] = 1'b1; // ESC
8'h52 : begin keys[8'd33] = 1'b1; keys[8'd53] = 1'b1; end // ! ////todo "Ä" on german keyboard
//8'h52 : begin keys[8'd34] = 1'b1; keys[8'd53] = 1'b1; end // " ////todo shift GALAKSIJA
8'h12 : keys[8'd53] = 1'b1; // SHIFT L
8'h59 : keys[8'd53] = 1'b1; // SHIFT R
endcase
if (keys[8'd53] == 1'b1) begin//shift
case (ps2_key[7:0])
8'h1C : keys[8'd01] = 1'b1; // a
8'h32 : keys[8'd02] = 1'b1; // b
8'h21 : keys[8'd03] = 1'b1; // c
8'h23 : keys[8'd04] = 1'b1; // d
8'h24 : keys[8'd05] = 1'b1; // e
8'h2B : keys[8'd06] = 1'b1; // f
8'h34 : keys[8'd07] = 1'b1; // g
8'h33 : keys[8'd08] = 1'b1; // h
8'h43 : keys[8'd09] = 1'b1; // i
8'h3B : keys[8'd10] = 1'b1; // j
8'h42 : keys[8'd11] = 1'b1; // k
8'h4B : keys[8'd12] = 1'b1; // l
8'h3A : keys[8'd13] = 1'b1; // m
8'h31 : keys[8'd14] = 1'b1; // n
8'h44 : keys[8'd15] = 1'b1; // O
8'h4D : keys[8'd16] = 1'b1; // p
8'h15 : keys[8'd17] = 1'b1; // q
8'h2D : keys[8'd18] = 1'b1; // r
8'h1B : keys[8'd19] = 1'b1; // s
8'h2C : keys[8'd20] = 1'b1; // t
8'h3C : keys[8'd21] = 1'b1; // u
8'h2A : keys[8'd22] = 1'b1; // v
8'h1D : keys[8'd23] = 1'b1; // w
8'h22 : keys[8'd24] = 1'b1; // x
8'h35 : keys[8'd25] = 1'b1; // y
8'h1A : keys[8'd26] = 1'b1; // z
endcase
end;
if (rd_key) key_out <= (keys[addr]==1) ? 8'hfe : 8'hff;
end
endmodule

View File

@ -0,0 +1,256 @@
module galaksija_keyboard2(
input clk,
input reset_n,
input [5:0]addr,
input rd_key,
input RD_n,
input ps2_clk,
input ps2_data,
input LINE_IN,
output [7:0]KDatout
);
wire [2:0]KSsel = addr[2:0];
wire [2:0]KRsel = addr[5:3];
wire [7:0]KS;
wire [2:0]KR_bin;
//wire KSout;
wire [7:0]scan_code, scan_code_int;
wire scan_ready, scan_ready_int;
wire [2:0]row, col;
wire set, clr;
typedef reg [0:63] arr;
arr key_array = 8'hFF;
wire special, special_set, special_clr;
typedef enum {WAIT_CODE, RELEASE} STATES;
STATES CState, NState = WAIT_CODE;
wire kbd_rd;
// Select keyboard row or select latch
always @(KRsel, rd_key)
begin
if (rd_key == 1'b1) begin
case (KRsel)//spalte
3'b000 : KR_bin <= 3'b000;
3'b001 : KR_bin <= 3'b001;
3'b010 : KR_bin <= 3'b010;
3'b011 : KR_bin <= 3'b011;
3'b100 : KR_bin <= 3'b100;
3'b101 : KR_bin <= 3'b101;
3'b110 : KR_bin <= 3'b110;
3'b111 : KR_bin <= 3'b111;
default : KR_bin <= 3'b000;
endcase
end else
KR_bin <= 3'b000;
end
// Multiplex the keyboard scanlines
always @(KSsel, rd_key, KS, RD_n)
begin
KDatout <= 8'b00000000;
case (KSsel)//reihe
3'b000 : KDatout[0] <= KS[0];
3'b001 : KDatout[1] <= KS[1];
3'b010 : KDatout[2] <= KS[2];
3'b011 : KDatout[3] <= KS[3];
3'b100 : KDatout[4] <= KS[4];
3'b101 : KDatout[5] <= KS[5];
3'b110 : KDatout[6] <= KS[6];
3'b111 : KDatout[7] <= KS[7];
default : KDatout <= 8'b11111111;
endcase
end
// scan_ready_int has asynchronous reset
always @(scan_ready_int, clk) begin
if (clk == 1'b1) begin
scan_ready = scan_ready_int;
scan_code = scan_code_int;
end
end
// Galaksija keyboard array
always @(KR_bin, row, col, set, clr, clk, LINE_IN, key_array) begin
{row,col} = 6'b000000;
if (LINE_IN == 1'b1) begin
if (KR_bin == ~3'b000)
KS[0] = {3'b000,KR_bin};
else
KS[0] = 1'b1;
end else
KS[0] = 1'b0;
KS[1] = {3'b001,KR_bin};
KS[2] = {3'b010,KR_bin};
KS[3] = {3'b011,KR_bin};
KS[4] = {3'b100,KR_bin};
KS[5] = {3'b101,KR_bin};
KS[6] = {3'b110,KR_bin};
KS[7] = {3'b111,KR_bin};
if (clk == 1'b1) begin
if (set == 1'b1)
{row,col} = 6'b111111;
else if (clr == 1'b1) begin
{row,col} = 6'b000000;
end
end
end
// Bit for special characters
always @(special_set, special_clr, clk) begin
if (clk == 1'b1) begin
if (special_clr == 1'b1)
special = 1'b0;
if (special_set == 1'b1)
special = 1'b1;
end
end
// Capture special codes
always @(scan_code, scan_ready) begin
if (scan_ready == 1'b1) begin
if (scan_code == 8'hE0)
special_set = 1'b1;
else
special_set = 1'b0;
end else
special_set = 1'b0;
end
// State machine state propagation
always @(clk, NState, reset_n) begin
if (reset_n == 1'b0)
CState = WAIT_CODE;
else
if (clk == 1'b1)
CState = NState;
end
// State machine
always @(CState, scan_code, scan_ready) begin
case (CState)
WAIT_CODE : begin
set = 1'b0;
special_clr = 1'b0;
if (scan_ready == 1'b1) begin
kbd_rd <= 1'b1;
if (scan_code == 8'hF0) begin
NState = RELEASE;
clr = 1'b0;
end else begin
NState = WAIT_CODE;
clr = 1'b1;
end
end else begin
kbd_rd = 1'b0;
clr = 1'b0;
NState = WAIT_CODE;
end
end
RELEASE : begin
clr = 1'b0;
if (scan_ready == 1'b1) begin
kbd_rd = 1'b1;
set = 1'b1;
NState = WAIT_CODE;
special_clr = 1'b1;
end else begin
kbd_rd = 1'b0;
set = 1'b0;
NState = RELEASE;
special_clr = 1'b0;
end
end
endcase
end
always @(special, scan_code) begin
if (special == 1'b0)
case (scan_code)
8'h1C : begin row = "001"; row = "000"; end// A
8'h32 : begin row = "010"; row = "000"; end// B
8'h21 : begin row = "011"; row = "000"; end// C
8'h23 : begin row = "100"; row = "000"; end// D
8'h24 : begin row = "101"; row = "000"; end// E
8'h2B : begin row = "110"; row = "000"; end// F
8'h34 : begin row = "111"; row = "000"; end// G
8'h33 : begin row = "000"; row = "001"; end// H
8'h43 : begin row = "001"; row = "001"; end// I
8'h3B : begin row = "010"; row = "001"; end// J
8'h42 : begin row = "011"; row = "001"; end// K
8'h4B : begin row = "100"; row = "001"; end// L
8'h3A : begin row = "101"; row = "001"; end// M
8'h31 : begin row = "110"; row = "001"; end// N
8'h44 : begin row = "111"; row = "001"; end// O
8'h4D : begin row = "000"; row = "010"; end// P
8'h15 : begin row = "001"; row = "010"; end// Q
8'h2D : begin row = "010"; row = "010"; end// R
8'h1B : begin row = "011"; row = "010"; end// S
8'h2C : begin row = "100"; row = "010"; end// T
8'h3C : begin row = "101"; row = "010"; end// U
8'h2A : begin row = "110"; row = "010"; end// V
8'h1D : begin row = "111"; row = "010"; end// W
8'h22 : begin row = "000"; row = "011"; end// X
8'h35 : begin row = "001"; row = "011"; end// Y
8'h1A : begin row = "010"; row = "011"; end// Z
8'h29 : begin row = "111"; row = "011"; end// SPACE
8'h45 : begin row = "000"; row = "100"; end// 0
8'h16 : begin row = "001"; row = "100"; end// 1
8'h1E : begin row = "010"; row = "100"; end// 2
8'h26 : begin row = "011"; row = "100"; end// 3
8'h25 : begin row = "100"; row = "100"; end// 4
8'h2E : begin row = "101"; row = "100"; end// 5
8'h36 : begin row = "110"; row = "100"; end// 6
8'h3D : begin row = "111"; row = "100"; end// 7
8'h3E : begin row = "000"; row = "101"; end// 8
8'h46 : begin row = "001"; row = "101"; end// 9
8'h4C : begin row = "010"; row = "101"; end// ;
8'h54 : begin row = "011"; row = "101"; end// : (PS2 equ = [)
8'h41 : begin row = "100"; row = "101"; end// ,
8'h55 : begin row = "101"; row = "101"; end// =
8'h71 : begin row = "110"; row = "101"; end// .
8'h49 : begin row = "110"; row = "101"; end// .
8'h4A : begin row = "111"; row = "101"; end// /
8'h5A : begin row = "000"; row = "110"; end// ret
8'h12 : begin row = "101"; row = "110"; end// shift (left)
8'h59 : begin row = "101"; row = "110"; end// shift (right)
default : begin row = "111"; col = "111"; end
endcase
else
case (scan_code)
8'h75 : begin row = "011"; row = "011"; end// UP
8'h72 : begin row = "100"; row = "011"; end// DOWN
8'h6B : begin row = "101"; row = "011"; end// LEFT
8'h74 : begin row = "110"; row = "011"; end// RIGHT
8'h4A : begin row = "111"; row = "101"; end// /
8'h69 : begin row = "001"; row = "110"; end// brk = end
8'h6C : begin row = "010"; row = "110"; end// rpt = home
8'h71 : begin row = "011"; row = "110"; end// del
8'h7D : begin row = "100"; row = "110"; end// lst = page up
default : begin row = "111"; col = "111"; end
endcase
end
keyboard keyboard(
.keyboard_clk(ps2_clk),
.keyboard_data(ps2_data),
.clock(clk),
.reset(reset_n),
.reads(kbd_rd),
.scan_code(scan_code_int),
.scan_ready(scan_ready_int)
);
endmodule

View File

@ -1,8 +1,11 @@
module galaksija_top(
input sysclk,
input vidclk,
input cpuclk,
input audclk,
input reset_in,
input [10:0] ps2_key,
input ps2_clk,
input ps2_data,
output [7:0] audio,
input cass_in,
output cass_out,
@ -16,7 +19,7 @@ reg [6:0] reset_cnt = 0;
wire cpu_resetn = reset_cnt[6];
reg [31:0] int_cnt = 0;
always @(posedge sysclk) begin
always @(posedge vidclk) begin
if(reset_in == 0)
reset_cnt <= 0;
else if(cpu_resetn == 0)
@ -53,7 +56,7 @@ T80s #(
.IOWait(1))
cpu(
.RESET_n(cpu_resetn),
.CLK_n(~sysclk),
.CLK_n(~cpuclk),
.WAIT_n(1'b1),
.INT_n(int_n),
.NMI_n(nmi_n),
@ -74,26 +77,26 @@ cpu(
wire [7:0] rom1_out;
reg rd_rom1;
sprom #(
sprom #(//4k
.init_file("./roms/ROM1.hex"),
.widthad_a(12),
.width_a(8))
rom1(
.address(addr[11:0]),
.clock(sysclk & rd_rom1),
.clock(cpuclk & rd_rom1),
.q(rom1_out)
);
wire [7:0] rom2_out;
reg rd_rom2;
sprom #(
sprom #(//4k
.init_file("./roms/ROM2.hex"),
.widthad_a(12),
.width_a(8))
rom2(
.address(addr[11:0]),
.clock(sysclk & rd_rom2),
.clock(cpuclk & rd_rom2),
.q(rom2_out)
);
@ -101,19 +104,19 @@ rom2(
wire [7:0] rom3_out;
reg rd_rom3;
sprom #(
sprom #(//4k
.init_file("./roms/galplus.hex"),
.widthad_a(12),
.width_a(8))
rom3(
.address(addr[11:0]),
.clock(sysclk & rd_rom3),
.clock(cpuclk & rd_rom3),
.q(rom3_out)
);
reg rd_mram, wr_mram;
reg rd_mram0, wr_mram0;
wire cs_mram0 = ~addr[15] & ~addr[14];
wire we_mram0 = wr_mram & cs_mram0;
wire we_mram0 = wr_mram0 & cs_mram0;
wire [7:0] mram0_out;
spram #(//2k
@ -121,14 +124,15 @@ spram #(//2k
.width_a(8))
ram00(
.address(addr[10:0]),
.clock(sysclk),
.clock(cpuclk),
.wren(we_mram0),
.data(odata),
.q(mram0_out)
);
reg rd_mram1, wr_mram1;
wire cs_mram1 = ~addr[15] & addr[14];
wire we_mram1 = wr_mram & cs_mram1;
wire we_mram1 = wr_mram1 & cs_mram1;
wire [7:0] mram1_out;
spram #(//2k
@ -136,14 +140,15 @@ spram #(//2k
.width_a(8))
ram01(
.address(addr[10:0]),
.clock(sysclk),
.clock(cpuclk),
.wren(we_mram1),
.data(odata),
.q(mram1_out)
);
reg rd_mram2, wr_mram2;
wire cs_mram2 = addr[15] & ~addr[14];
wire we_mram2 = wr_mram & cs_mram2;
wire we_mram2 = wr_mram2 & cs_mram2;
wire [7:0] mram2_out;
spram #(//16k
@ -151,14 +156,15 @@ spram #(//16k
.width_a(8))
ram02(
.address(addr[13:0]),
.clock(sysclk),
.clock(cpuclk),
.wren(we_mram2),
.data(odata),
.q(mram2_out)
);
reg rd_mram3, wr_mram3;
wire cs_mram3 = addr[15] & addr[14];
wire we_mram3 = wr_mram & cs_mram3;
wire we_mram3 = wr_mram3 & cs_mram3;
wire [7:0] mram3_out;
spram #(//16k
@ -166,7 +172,7 @@ spram #(//16k
.width_a(8))
ram03(
.address(addr[13:0]),
.clock(sysclk),
.clock(cpuclk),
.wren(we_mram3),
.data(odata),
.q(mram3_out)
@ -177,27 +183,27 @@ reg wr_vram;
wire [7:0] vram_out;
galaksija_video#(
.h_visible(10'd640),
.h_front(10'd16),
.h_sync(10'd96),
.h_back(10'd48),
.v_visible(10'd480),
.v_front(10'd10),
.v_sync(10'd2),
.v_back(10'd33))
.h_visible(10'd640),
.h_front(10'd16),
.h_sync(10'd96),
.h_back(10'd48),
.v_visible(10'd480),
.v_front(10'd10),
.v_sync(10'd2),
.v_back(10'd33))
galaksija_video(
.clk(sysclk),
.resetn(reset_in),
.vga_dat(video_dat),
.vga_hsync(video_hs),
.vga_vsync(video_vs),
.vga_blank(video_blank),
.rd_ram1(rd_vram),
.wr_ram1(wr_vram),
.ram1_out(vram_out),
.addr(addr[10:0]),
.data(odata)
);
.clk(vidclk),
.resetn(reset_in),
.vga_dat(video_dat),
.vga_hsync(video_hs),
.vga_vsync(video_vs),
.vga_blank(video_blank),
.rd_ram1(rd_vram),
.wr_ram1(wr_vram),
.ram1_out(vram_out),
.addr(addr[10:0]),
.data(odata)
);
reg wr_latch;
@ -207,9 +213,15 @@ galaksija_video(
rd_rom2 = 1'b0;
rd_rom3 = 1'b0;
rd_vram = 1'b0;
rd_mram = 1'b0;
rd_mram0 = 1'b0;
rd_mram1 = 1'b0;
rd_mram2 = 1'b0;
rd_mram3 = 1'b0;
wr_vram = 1'b0;
wr_mram = 1'b0;
wr_mram0 = 1'b0;
wr_mram1 = 1'b0;
wr_mram2 = 1'b0;
wr_mram3 = 1'b0;
rd_key = 1'b0;
wr_latch = 1'b0;
@ -225,154 +237,57 @@ galaksija_video(
{3'b010,16'b00101xxxxxxxxxxx}: begin idata = vram_out; rd_vram = 1'b1; end
{3'b100,16'b00101xxxxxxxxxxx}: wr_vram= 1'b1;
//$3000...$37FF — RAM "D": 2 KB
{3'b010,16'b00110xxxxxxxxxxx}: begin idata = mram0_out; rd_mram = 1'b1; end
{3'b100,16'b00110xxxxxxxxxxx}: wr_mram= 1'b1;
{3'b010,16'b00110xxxxxxxxxxx}: begin idata = mram0_out; rd_mram0 = 1'b1; end
{3'b100,16'b00110xxxxxxxxxxx}: wr_mram0= 1'b1;
//$3800...$3FFF — RAM "E": 2 KB
{3'b010,16'b00111xxxxxxxxxxx}: begin idata = mram1_out; rd_mram = 1'b1; end
{3'b100,16'b00111xxxxxxxxxxx}: wr_mram= 1'b1;
{3'b010,16'b00111xxxxxxxxxxx}: begin idata = mram1_out; rd_mram1 = 1'b1; end
{3'b100,16'b00111xxxxxxxxxxx}: wr_mram1= 1'b1;
//$4000...$7FFF — RAM IC9, IC10: 16 KB
{3'b010,16'b01xxxxxxxxxxxxxx}: begin idata = mram2_out; rd_mram = 1'b1; end
{3'b100,16'b01xxxxxxxxxxxxxx}: wr_mram= 1'b1;
{3'b010,16'b01xxxxxxxxxxxxxx}: begin idata = mram2_out; rd_mram2 = 1'b1; end
{3'b100,16'b01xxxxxxxxxxxxxx}: wr_mram2= 1'b1;
//$8000...$BFFF — RAM IC11, IC12: 16 KB
{3'b010,16'b10xxxxxxxxxxxxxx}: begin idata = mram3_out; rd_mram = 1'b1; end
{3'b100,16'b10xxxxxxxxxxxxxx}: wr_mram= 1'b1;
{3'b010,16'b10xxxxxxxxxxxxxx}: begin idata = mram3_out; rd_mram3 = 1'b1; end
{3'b100,16'b10xxxxxxxxxxxxxx}: wr_mram3= 1'b1;
//$E000...$FFFF — ROM "3" + "4" IC13: 8 KB Graphic primitives in BASIC language, Full Screen Source Editor and soft scrolling
{3'b010,16'b1110000000000000}: begin idata = rom3_out; rd_rom3 = 1'b1; end
//default :
default : begin end
endcase
end
wire [7:0]key_out;
reg keys[63:0];
reg rd_key;
integer num;
initial
begin
for(num=0;num<64;num=num+1)
begin
keys[num] <= 0;
end
end
always @(posedge sysclk) begin
if (rd_key) key_out <= (keys[addr[5:0]]==1) ? 8'hfe : 8'hff;
if(sysclk)
begin
for(num=0;num<64;num=num+1)
begin
keys[num] = 1'b0;
end
case (ps2_key[7:0])
//nix 00
8'h1C : keys[8'd01] = 1'b1; // A
8'h32 : keys[8'd02] = 1'b1; // B
8'h21 : keys[8'd03] = 1'b1; // C
8'h23 : keys[8'd04] = 1'b1; // D
8'h24 : keys[8'd05] = 1'b1; // E
8'h2B : keys[8'd06] = 1'b1; // F
8'h34 : keys[8'd07] = 1'b1; // G
8'h33 : keys[8'd08] = 1'b1; // H
8'h43 : keys[8'd09] = 1'b1; // I
8'h3B : keys[8'd10] = 1'b1; // J
8'h42 : keys[8'd11] = 1'b1; // K
8'h4B : keys[8'd12] = 1'b1; // L
8'h3A : keys[8'd13] = 1'b1; // M
8'h31 : keys[8'd14] = 1'b1; // N
8'h44 : keys[8'd15] = 1'b1; // O
8'h4D : keys[8'd16] = 1'b1; // P
8'h15 : keys[8'd17] = 1'b1; // Q
8'h2D : keys[8'd18] = 1'b1; // R
8'h1B : keys[8'd19] = 1'b1; // S
8'h2C : keys[8'd20] = 1'b1; // T
8'h3C : keys[8'd21] = 1'b1; // U
8'h2A : keys[8'd22] = 1'b1; // V
8'h1D : keys[8'd23] = 1'b1; // W
8'h22 : keys[8'd24] = 1'b1; // X
8'h35 : keys[8'd25] = 1'b1; // Y
8'h1A : keys[8'd26] = 1'b1; // Z
//nix 27,28,30,31
8'h66 : keys[8'd29] = 1'b1; // BACKSPACE
8'h29 : keys[8'd31] = 1'b1; // SPACE
8'h45 : keys[8'd32] = 1'b1; // 0
8'h16 : keys[8'd33] = 1'b1; // 1
8'h1E : keys[8'd34] = 1'b1; // 2
8'h26 : keys[8'd35] = 1'b1; // 3
8'h25 : keys[8'd36] = 1'b1; // 4
8'h2E : keys[8'd37] = 1'b1; // 5
8'h36 : keys[8'd38] = 1'b1; // 6
8'h3D : keys[8'd39] = 1'b1; // 7
8'h3E : keys[8'd40] = 1'b1; // 8
8'h46 : keys[8'd41] = 1'b1; // 9
// NUM Block
8'h70 : keys[8'd32] = 1'b1; // 0
8'h69 : keys[8'd33] = 1'b1; // 1
8'h72 : keys[8'd34] = 1'b1; // 2
8'h7A : keys[8'd35] = 1'b1; // 3
8'h6B : keys[8'd36] = 1'b1; // 4
8'h73 : keys[8'd37] = 1'b1; // 5
8'h74 : keys[8'd38] = 1'b1; // 6
8'h6C : keys[8'd39] = 1'b1; // 7
8'h75 : keys[8'd40] = 1'b1; // 8
8'h7D : keys[8'd41] = 1'b1; // 9
8'h4C : keys[8'd42] = 1'b1; // ; //todo "Ö" on german keyboard
8'h7C : keys[8'd43] = 1'b1; // : //todo NUM block for now
8'h41 : keys[8'd44] = 1'b1; // ,
8'h55 : keys[8'd45] = 1'b1; // = ////todo "´" on german keyboard
8'h49 : keys[8'd46] = 1'b1; // .
8'h4A : keys[8'd47] = 1'b1; // /
8'h5A : keys[8'd48] = 1'b1; // ENTER
8'h76 : keys[8'd49] = 1'b1; // ESC
8'h52 : begin keys[8'd33] = 1'b1; keys[8'd53] = 1'b1; end // ! ////todo "Ä" on german keyboard
//8'h52 : begin keys[8'd34] = 1'b1; keys[8'd53] = 1'b1; end // " ////todo shift GALAKSIJA
8'h12 : keys[8'd53] = 1'b1; // SHIFT L
8'h59 : keys[8'd53] = 1'b1; // SHIFT R
/*
8'h1C : keys[8'd01] = 1'b1; // a
8'h32 : keys[8'd02] = 1'b1; // b
8'h21 : keys[8'd03] = 1'b1; // c
8'h23 : keys[8'd04] = 1'b1; // d
8'h24 : keys[8'd05] = 1'b1; // e
8'h2B : keys[8'd06] = 1'b1; // f
8'h34 : keys[8'd07] = 1'b1; // g
8'h33 : keys[8'd08] = 1'b1; // h
8'h43 : keys[8'd09] = 1'b1; // i
8'h3B : keys[8'd10] = 1'b1; // j
8'h42 : keys[8'd11] = 1'b1; // k
8'h4B : keys[8'd12] = 1'b1; // ,
8'h3A : keys[8'd13] = 1'b1; // m
8'h31 : keys[8'd14] = 1'b1; // n
8'h44 : keys[8'd15] = 1'b1; // O
8'h4D : keys[8'd16] = 1'b1; // p
8'h15 : keys[8'd17] = 1'b1; // q
8'h2D : keys[8'd18] = 1'b1; // r
8'h1B : keys[8'd19] = 1'b1; // s
8'h2C : keys[8'd20] = 1'b1; // t
8'h3C : keys[8'd21] = 1'b1; // u
8'h2A : keys[8'd22] = 1'b1; // v
8'h1D : keys[8'd23] = 1'b1; // w
8'h22 : keys[8'd24] = 1'b1; // x
8'h35 : keys[8'd25] = 1'b1; // y
8'h1A : keys[8'd26] = 1'b1; // z*/
endcase
end
end
wire rd_key;
galaksija_keyboard1 galaksija_keyboard1(
.clk(vidclk),
.addr(addr[5:0]),
.reset(~reset_in),
.ps2_key(ps2_key),
.key_out(key_out),
.rd_key(rd_key)
);
/*
galaksija_keyboard2 galaksija_keyboard2(
.clk(vidclk),
.reset_n(reset_in),
.addr(addr[5:0]),
.rd_key(rd_key),
.RD_n(rd_n),
.ps2_clk(ps2_clk),
.ps2_data(ps2_data),
.LINE_IN(1'b0),
.KDatout(key_out)
);*/
wire PIN_A = (1'b1 & 1'b1 & wr_n);
wire [7:0]chan_A, chan_B, chan_C;
wire A02 = ~(C00 | PIN_A);//nor
wire B02 = ~(C00 | addr[0]);//nor
wire D02 = ~(addr[6] | iorq_n);//nor
wire C00 = ~(D02 | m1_n);//nand
wire A02 = ~(C00 | PIN_A);
wire B02 = ~(C00 | addr[0]);
wire D02 = ~(addr[6] | iorq_n);
wire C00 = ~(D02 & m1_n);
assign audio = chan_A & chan_B & chan_C;
AY8912 AY8912(
.CLK(sysclk),
.CLK(vidclk),
.CE(audclk),
.RESET(~reset_in),
.BDIR(A02),
@ -385,6 +300,6 @@ AY8912 AY8912(
.SEL(1'b1),//divider?
.IO_in(),//not used
.IO_out()//not used
);
);
endmodule

View File

@ -0,0 +1,81 @@
--
-- PS2 keyboard
--
LIBRARY IEEE;
USE IEEE.STD_LOGIC_1164.all;
USE IEEE.STD_LOGIC_ARITH.all;
USE IEEE.STD_LOGIC_UNSIGNED.all;
ENTITY keyboard IS
PORT( keyboard_clk, keyboard_data, clock ,
reset, reads : IN STD_LOGIC;
scan_code : OUT STD_LOGIC_VECTOR(7 DOWNTO 0);
scan_ready : OUT STD_LOGIC);
END keyboard;
ARCHITECTURE rtl OF keyboard IS
SIGNAL INCNT : std_logic_vector(3 downto 0);
SIGNAL SHIFTIN : std_logic_vector(8 downto 0);
SIGNAL READ_CHAR, clock_enable : std_logic;
SIGNAL ready_set : std_logic;
SIGNAL keyboard_clk_filtered : std_logic;
SIGNAL filter : std_logic_vector(7 downto 0);
BEGIN
PROCESS (reads, ready_set)
BEGIN
IF reads = '1' THEN scan_ready <= '0';
ELSIF ready_set'EVENT and ready_set = '1' THEN
scan_ready <= '1';
END IF;
END PROCESS;
--This process filters the raw clock signal coming from the keyboard using a shift register and two AND gates
Clock_filter: PROCESS
BEGIN
WAIT UNTIL clock'EVENT AND clock= '1';
clock_enable <= NOT clock_enable;
IF clock_enable = '1' THEN
filter (6 DOWNTO 0) <= filter(7 DOWNTO 1) ;
filter(7) <= keyboard_clk;
IF filter = "11111111" THEN keyboard_clk_filtered <= '1';
ELSIF filter= "00000000" THEN keyboard_clk_filtered <= '0';
END IF;
END IF;
END PROCESS Clock_filter;
--This process reads in serial data coming from the terminal
PROCESS
BEGIN
WAIT UNTIL (KEYBOARD_CLK_filtered'EVENT AND KEYBOARD_CLK_filtered='1');
IF RESET='0' THEN
INCNT <= "0000";
READ_CHAR <= '0';
ready_set<= '0';
ELSE
IF KEYBOARD_DATA='0' AND READ_CHAR='0' THEN
READ_CHAR<= '1';
ready_set<= '0';
ELSE
-- Shift in next 8 data bits to assemble a scan code
IF READ_CHAR = '1' THEN
IF INCNT < "1001" THEN
INCNT <= INCNT + 1;
SHIFTIN(7 DOWNTO 0) <= SHIFTIN(8 DOWNTO 1);
SHIFTIN(8) <= KEYBOARD_DATA;
-- End of scan code character, so set flags and exit loop
ELSE
scan_code <= SHIFTIN(7 DOWNTO 0);
READ_CHAR <= '0';
ready_set <= '1';
INCNT <= "0000";
END IF;
END IF;
END IF;
END IF;
END PROCESS;
END rtl;